目录

4.1约克托项目组件

4.1.1比特贝克

4.1.2食谱recips

4.1.3类class

4.1.4配置conf

4.2层layer

4.3开放式构建系统概念

4.3.1用户配置

4.3.2元数据、机器配置和策略配置

4.3.2.1  distro

4.3.3来源

4.3.4包装馈送

4.3.5比特巴克工具

4.3.5.2 Patching

4.3.6图像

4.3.7应用开发SDK

4.4交叉开发工具链生成

4.5共享状态缓存

4.5.1总体架构

4.5.2校验和(签名)

4.5.3共享状态

4.6自动添加运行时依赖

4.7 Fakeroot 和 Pseudo


本章为Yocto项目概念提供了解释,这些概念超越了"如何"信息和参考(或查找)材料的表面。解释了组件、开放式构建系统工作流程、交叉开发工具链、共享状态缓存等概念。

4.1约克托项目组件

BitBake任务执行器以及各种类型的配置文件组成了开放式核心 (OE-Core)。本节通过描述这些组件的使用及其交互方式来概述这些组件。

BitBake 处理数据文件的解析和执行。数据本身是多种类型的:

  • 食谱:提供有关特定软件的详细信息。

  • 类数据:摘要常见构建信息(例如,如何构建 Linux 内核)。

  • 配置数据:定义机器特定设置、策略决策等。配置数据充当将所有内容结合在一起的粘合剂。

BitBake 知道如何将多个数据源组合在一起,并将每个数据源称为一层。有关图层的信息,请参阅 Yocto 项目开发任务手册中的"理解和创建层"部分。

以下是有关这些核心组件的一些简短细节。有关这些组件在构建过程中如何相互作用的其他信息,

请参阅"开放式构建系统概念"部分。

4.1.1比特贝克

BitBake 是开放式构建系统的核心工具,负责解析元数据,从中生成任务列表,然后执行这些任务。

本节简要介绍了 BitBake。如果您想要有关 BitBake 的更多信息,请参阅位贝克用户手册。

要查看 BitBake 支持的选项列表,请使用以下任一命令:

$ bitbake -h
$ bitbake --help

BitBake 最常见的用法是,您想要构建的配方的名称(称为"目标")。目标通常等同于食谱文件名的第一部分(例如,名为"foo"的食谱)。因此,要处理配方文件,您可以键入以下类型:bitbake recipenamerecipenamefoo_1.3.0-r0.bbmatchbox-desktop_1.2.3.bb

$ bitbake matchbox-desktop

可能存在几个不同版本。BitBake 会选择按分配配置选择的。您可以在 BitBake 用户手册的"首选项"部分获得有关 BitBake 如何在不同目标版本和提供商之间进行选择的更多详细信息。matchbox-desktop

BitBake 还尝试先执行任何受抚养的任务。因此,例如,在构建之前,BitBake 将构建一个交叉编译器,如果尚未构建。matchbox-desktopglibc

需要考虑的有用 BitBake 选项是该选项或选项。此选项指示 BitBake 即使在遇到错误后,也尝试尽可能长时间地继续处理工作。当发生错误时,无法重新制造失败的目标和依赖错误的目标。但是,当您使用此选项时,仍可以处理其他依赖关系。-k--continue

4.1.2食谱recips

具有后缀的文件是"食谱"文件。一般来说,食谱包含有关单个软件的信息。此信息包括下载未改变源的位置、应用于该源的任何源补丁(如果需要),应用哪些特殊配置选项、如何编译源文件以及如何打包编译的输出。.bb

术语"包"有时用于指食谱。但是,由于"包"一词用于来自 OpenEmbedd 构建系统的包装输出(即。 或文件),本文档避免使用术语"包"时,指的是食谱。.ipk.deb

4.1.3类class

类文件 () 包含可用于在食谱文件之间共享的信息。例如自动工具类,它包含自动工具使用的任何应用程序的常见设置。Yocto 项目参考手册中的"类"一章提供了有关课程以及如何使用它们的详细信息。.bbclass

4.1.4配置conf

配置文件 () 定义管理开放式构建过程的各种配置变量。这些文件分为几个领域,定义机器配置选项,分配配置选项,编译器调谐选项,一般常见的配置选项,和用户配置选项,这是在构建目录中找到的。.confconf/local.conf

4.2层layer

层是包含相关元数据(即一组指令)的存储库,可告诉 OpenEmbedd 构建系统如何构建目标。 Yocto 项目层模型可促进 Yocto 项目开发环境中的合作、共享、定制和再利用。从逻辑上讲,为您的项目划分信息层。例如,您可以使用一层来保留特定硬件的所有配置。隔离特定于硬件的配置允许您使用不同的层来共享其他元数据,其中元数据在几个硬件中可能很常见。

在 Yocto 项目开发环境中有许多层工作。Yocto 项目策划层索引和开放式层索引都包含您可以使用或利用的层。

按照惯例,Yocto 项目的层遵循特定形式。符合已知结构允许 BitBake 在构建到查找元数据类型时做出假设。您可以在《Yocto 项目开发任务手册》的"理解和创建层"部分找到创建适合 Yocto 项目的图层的程序并了解工具(即)。bitbake-layers

4.3开放式构建系统概念

本节对开放式构建系统(Yocto 项目特有的构建系统)使用的构建过程进行了更详细的了解。构建系统的核心是任务执行者 BitBake。

下图表示构建的高级别工作流。本节的其余部分扩展了构成工作流程的基本输入、输出、过程和元数据逻辑块。

一般来说,构建的工作流程由几个功能区组成:

  • 用户配置可用于控制构建过程的元数据。

  • 元数据层提供软件、机器和散数元数据的各种层。

  • 来源文件上游版本、本地项目和 SCM。

  • 构建系统比特贝克控制下的过程。此块扩展了 BitBake 获取源、应用修补程序、完成编译、分析封装生成输出、创建和测试封装、生成图像和生成交叉开发工具的情况。

  • 包装源包含输出包 (RPM、DEB 或 IPK) 的目录,这些输出包随后用于构建系统生成的图像或软件开发套件 (SDK)。如果启用了运行时间包管理,还可以使用 Web 服务器或其他方式复制和共享这些源,以方便在运行时间扩展或更新设备上的现有图像。

  • image:工作流生成的image。

  • 应用开发 SDK:与图像一起或与 BitBake 单独生成的交叉开发工具。

4.3.1用户配置

用户配置有助于定义构建。通过用户配置,您可以告诉 BitBake 您正在构建图像的目标架构、将下载的源存储在哪里以及其他构建属性。

下图显示了一般工作流程图的"用户配置"框的扩展表示:

BitBake 需要一些基本的配置文件才能完成构建。这些文件是文件。最不需要的作为示例文件在源目录中。简单来说,本节将源目录称为"Poky 目录"。*.confbuild/conf

当您克隆Poky Git 存储库或下载并解包 Yocto 项目版本时,您可以设置源目录以命名任何您想要的。对于此讨论,克隆存储库使用默认名称。poky

注意

Poky 存储库主要是现有存储库的聚合。它不是一个规范的上游来源。

Poky 内部的层包含具有示例配置文件的目录。这些示例文件用作创建实际配置文件的基础,当您 source oe-init-build-env时,这是构建环境脚本。meta-pokyconf

采购构建环境脚本创建构建目录(如果尚未存在)。BitBake 在构建过程中使用生成目录进行所有工作。构建目录包含包含您和配置文件的默认版本的目录。只有当版本在源构建环境设置脚本时尚未存在于构建目录中时,才会创建这些默认配置文件。

conflocal.conf

bblayers.conf

由于 Poky 存储库从根本上是现有存储库的聚合,因此一些用户可能熟悉在单独的OpenEmbedd-Core (OE-Core)和 BitBake 存储库(而不是单个 Poky 存储库)的背景下运行oe-init-build-env脚本。此讨论假定脚本是从 Poky 的克隆或未包装版本内执行的。

根据脚本的来源,不同的子脚本被调用以设置构建目录(Yocto 或打开已设)。具体来说,poky 目录中的脚本设置构建目录,并(如有必要)为目录进行种子,配置文件适合 Yocto 项目开发环境。scripts/oe-setup-builddir

注意

scripts/oe-setup-builddir script 使用变量来确定要定位的示例配置文件。

$TEMPLATECONF

该文件提供了许多定义构建环境的基本变量。下面是一些列表。要查看构建环境脚本创建的文件中的默认配置,请参阅图层中的local.conf.samplelocal.conflocal.confmeta-poky

  • 目标机器选择:由MACHINE 变量控制。

  • 下载目录:由DL_DIR变量控制。

  • 共享状态目录:由SSTATE_DIR变量控制。

  • 构建输出:由TMPDIR变量控制。

  • 分配政策:由DISTRO变量控制。

  • 包装格式:由PACKAGE_CLASSES变量控制。

  • SDK 目标架构:由SDKMACHINE变量控制。

  • 额外图像包:由EXTRA_IMAGE_FEATURES变量控制。

注意

 conf/local.conf 文件中设置的配置也可以设置在conf/site.conf conf/site.conf  配置文件中。

该文件告诉 BitBake 您希望在构建过程中考虑哪些层。默认情况下,此文件中列出的图层包括构建系统最不需要的层。但是,您必须手动添加您创建的任何自定义图层。您可以在 Yocto 项目开发任务手册中的"‎‎启用您的层‎‎"部分找到有关与文件合作的更多信息。‎bblayers.confbblayers.conf

‎文件不是由环境初始化脚本创建的。如果你想要的文件,你需要自己创建。该文件通常由自动建设者创建:‎

site.conf

auto.conf

site.conf

auto.conf

  • ‎site.conf: :‎‎您可以使用配置文件配置多个构建目录。例如,假设您有几个构建环境,它们具有一些共同的功能。您可以在此处设置这些默认构建属性。一个很好的例子也许是通过‎‎PACKAGE_CLASSES‎‎变量使用的包装格式。‎conf/site.conf

    ‎使用该文件的一个有用的方案是扩展您的‎‎BBPATH‎‎变量,包括路径到。然后,当 BitBake 使用‎‎BBPATH‎‎查找元数据时,它会找到该文件并应用文件中常见的配置。要覆盖特定构建目录中的配置,要更改该构建目录文件中的类似配置。‎conf/site.confconf/site.confconf/site.confconf/local.conf

  • ‎auto.conf::‎‎该文件通常由自动建设者创建并写入。放入文件的设置通常与在文件或文件中找到的设置相同。‎conf/local.confconf/site.conf

‎您可以编辑所有配置文件以进一步定义任何特定的构建环境。此过程由图中的"用户配置编辑"框表示。‎

‎当您使用命令启动构建时,BitBake 会整理出配置,以最终定义构建环境。重要的是要了解,‎‎开放式构建系统‎‎以特定顺序读取配置文件:并且,构建系统应用 BitBake 用户手册中的"‎‎语法和操作员‎‎"章节中描述的正常分配语句规则。由于文件按特定顺序解析,因此可能会影响同一变量的可变分配。例如,如果文件和设置的变量 1 到不同的值,因为构建系统解析后,可变 1 被分配从文件中的值。

bitbake targetsite.conf

auto.conf

local.confa

uto.conf

local.conf

local.conf

auto.conf

local.conf

4.3.2元数据、机器配置和策略配置

前一节描述了定义 BitBake 全球行为的用户配置。此部分更仔细地查看构建系统用于进一步控制构建的层。这些层为软件、机器和策略提供元数据。

一般来说,有三种类型的层输入。您可以在"用户配置"框下面看到一般工作流程图<查看手动/概念:打开的构建系统概念>:

  • 元Metadata (.bb + Patches): 包含用户提供的配方文件、补丁和附加文件的软件层。软件层的一个很好的示例可能是来自开放式层索引的元-qt5层。此层适用于桌面、嵌入式和移动的流行Qt跨平台应用开发框架的 5.0 版本。

  • Policy Configuration: 提供机器特定配置的板支持包 (BSP) 层(即下图中的"BSP 层")。此类信息特定于特定目标架构。参考分布 (Poky)中 BSP 层的一个很好的示例是元-yocto-bsp层。

  • 策略配置:分布层(如下图中的"Distro 层")为正在为特定分布而构建的图像或 SDK 提供顶级或一般策略。例如,在 Poky 参考分布中,散点层是元波基层。在 Distro 层中,有一个目录,其中包含了不一的配置文件(例如,包含许多用于 Poky 分布的政策配置的poky.conf)。conf/distro

下图从一般工作流程图中显示了这三层的扩展表示:

一般来说,所有层都有类似的结构。它们都包含一个许可文件(例如),如果要分发该层,则包含一个作为良好做法的文件,特别是要分发该层、配置目录和配方目录。您可以在 Yocto 项目开发任务手册中的"创建自己的层"部分了解与 Yocto 项目使用的层的总体结构。有关图层和可以绘制的多个层的一般讨论,请参阅本手册早期的"层"和"Yocto 项目层模型"部分。COPYING.MITREADME

如果您探索了以前的链接,您发现了一些与 Yocto 项目配合工作的层存在的区域。源存储库还显示在"Yocto 元数据层"下分类的图层。

注意

Yocto 项目源存储库中有一些层在开放式层索引中找不到。这种层要么被弃用,要么在性质上是实验性的。

BitBake 使用作为用户配置一部分的文件来查找它应该用作构建一部分的层。conf/bblayers.conf

4.3.2.1distro

分布层为您的分配提供策略配置。最佳实践要求您将这些类型的配置隔离到自己的层中。在覆盖 BitBake 在构建目录中的文件中找到的类似设置中提供的设置。conf/distro/distro.confconf/local.conf

下列列表提供了一些解释和参考,说明您通常在分布层中发现的内容:

  • classes: 类文件 () 具有可在分发中的配方之间共享的常见功能。当您的食谱继承一个类时,它们会承担该类的设置和功能。您可以在 Yocto 参考手册的"类"章节中有关类文件的内容。.bbclass

  • conf::此区域为该层()、分布()保存配置文件,任何分布范围都包含文件。conf/layer.confconf/distro/distro.conf

  • recipes- -:*配方和附加文件,影响整个分布的常见功能。此区域可以包括添加特定布局配置的配方和附加文件、初始化脚本、自定义图像配方等。目录的例子是和.目录中的层次结构和内容可能有所不同。通常,这些目录包含配方文件()、配方附加文件()、配置文件的不具体目录等。recipes-*recipes-corerecipes-extrarecipes-**.bb*.bbappend

4.3.2.2BSP 层

BSP 层提供针对特定硬件的机器配置。此层中的一切特定于您正在构建图像或 SDK 的机器。BSP 层定义了一个通用结构或形式。您可以在Yocto 项目委员会支持包开发人员指南中了解更多有关此结构的详细情况。

注意

为了使 BSP 层被视为符合 Yocto 项目,它必须满足某些结构要求。

BSP 层的配置目录包含机器()的配置文件,当然还有该层()。conf/machine/machine.confconf/layer.conf

层的其余部分是专门按功能特定的食谱:,,,等等。可以有多个外形器、图形支持系统等的元数据。recipes-bsprecipes-corerecipes-graphicsrecipes-kernel

注意

虽然图显示了几个食谱*目录,但并非所有这些目录都出现在所有 BSP 层中。

4.3.2.3软件层

软件层为构建过程中使用的其他软件包提供元数据。此层不包括特定于分布或机器的元数据,这些元数据位于其各自的层中。

此层包含项目所需的任何配方、附加文件和修补程序。

4.3.3来源

要使开放式构建系统创建图像或任何目标,它必须能够访问源文件。一般工作流程图表示使用"上游项目发布"、"本地项目"和"SCM(可选)"框的源文件。该图表示"源材料"框的后视镜,在定位源文件方面也起着一个作用。

源文件最终组织的方法是项目的一个函数。例如,对于已发布的软件,项目倾向于使用焦油球或其他存档文件,这些文件可以捕获可保证其静态表示的版本状态。另一方面,对于具有更动态或实验性质的项目,项目可能会将源文件保存在源控制管理器 (SCM)(如 Git)控制的存储库中。从存储库提取源可让您控制要构建软件的存储库(修订版)中的点。两者的结合也是可能的。

BitBake 使用SRC_URI变量指向源文件,无论其位置如何。每个配方必须有指向源的SRC_URI变量。

另一个在源文件来源中扮演重要角色的区域由DL_DIR变量指向。此区域是一个缓存,可以保留以前下载的源。您还可以指示 OpenEmbedd 构建系统从 Git 存储库创建焦油球,这不是默认行为,并使用BB_GENERATE_MIRROR_TARBALLS变量将其存储在DL_DIR中。

明智地使用DL_DIR目录可以节省构建系统在互联网上查找文件时的行程。使用下载目录的一个好方法是将DL_DIR指向构建目录以外的区域。这样做可以允许您在需要时安全地删除构建目录,而不必担心删除任何下载的源文件。

本节的其余部分提供了对源文件和后视镜的更深入的观察。以下是一般工作流程图的源文件区域的更详细的查看:

4.3.3.1上游项目发布

上游项目版本以存档文件(例如焦油球或拉链文件)的形式存在于任何地方。这些文件对应于单个食谱。例如,该图使用"忙碌盒"、Qt 和 Dbus 的每个版本。存档文件可用于使用配方构建的任何已发布的产品。

4.3.3.2本地项目

本地项目是用户提供的自定义软件位。这些位位于项目本地的某个地方 - 也许是用户检查项目(例如包含组使用的开发源树的本地目录)的目录。

包括本地项目的规范方法是使用外部src类来包括该本地项目。您使用或配方的附加文件来覆盖或设置配方指向磁盘上的本地目录以拉入整个源树。local.conf

4.3.3.3源控制经理(可选)

构建系统可以获取源文件的另一个地方是Fetchers使用各种源控制管理器 (SCM),如 Git 或颠覆。在这种情况下,存储库被克隆或检查出来。BitBake 内部的do_fetch任务使用SRC_URI变量和参数的前缀来确定正确的取件器模块。

注意

有关如何让 OpenEmbedd 构建系统生成 Git 存储库的焦油球并将其放入DL_DIR目录的信息,请参阅 Yocto 项目参考手册中的BB_GENERATE_MIRROR_TARBALLS变量。

取取存储库时,BitBake 使用SRCREV变量来确定构建的具体修订。

4.3.4包装馈送

当 OpenEmbedd 生成生成图像或 SDK 时,它会从位于构建目录中的包馈送区域获取包。一般工作流程图显示此包在右上角的馈送区域。

此部分看起来更接近构建系统使用的包源区域。以下是对该地区的更详细的了解:

包装源是构建过程中的中间步骤。OpenEmbedd 构建系统提供生成不同包类型的类,并指定通过PACKAGE_CLASSES变量启用哪些类。在将包装放入包装源之前,构建过程通过疯狂类对生成的输出质量保证检查进行验证。

包装馈送区域位于构建目录中。构建系统用于临时存储封装的目录由变量和使用中的特定封装管理器的组合决定。请参阅插图中的"包装源"框,并注意该区域右侧的信息。特别是,以下定义了包裹文件的保存位置:

  • DEPLOY_DIR: 定义为在生成目录中。tmp/deploy

  • DEPLOY_DIR_*:根据使用的包装管理器,包装类型子文件夹。鉴于 RPM、IPK 或 DEB 包装和焦油球的创建,分别使用DEPLOY_DIR_RPM、DEPLOY_DIR_IPK、DEPLOY_DIR_DEB或DEPLOY_DIR_TAR变量。

  • PACKAGE_ARCH: 定义架构特定的子文件夹。例如,i586 或 qemux86 架构的软件包可用。

BitBake 使用do_package_write_*任务生成包并将其放入封装保留区域(例如。 IPK 包)。请参阅 Yocto 项目参考手册中的"do_package_write_deb"、"do_package_write_ipk"、"do_package_write_rpm"和"do_package_write_tar"部分,了解更多信息。例如,考虑使用 IPK 包装管理器,并且同时为 i586 和 qemux86 提供包装架构支持的情况。i586 架构的封装被放置在中,而 qemux86 架构的封装则放在中。do_package_write_ipkbuild/tmp/deploy/ipk/i586build/tmp/deploy/ipk/qemux86

4.3.5比特巴克工具

开放式构建系统使用BitBake生成图像和软件开发套件 (SDK)。从一般工作流程图中可以看出,BitBake 区域由几个功能区组成。本节仔细查看了这些区域中的每个区域。

注意

BitBake 工具的文档单独提供。有关比特贝克的参考材料,请参阅比特贝克用户手册。

4.3.5.1源获取

构建配方的第一阶段是获取和拆开源代码:

do_fetch和do_unpack任务获取源文件,并将其解包到生成目录中。

注意

对于每个作为配方SRC_URI语句一部分的本地文件(例如 file://),OpenEmbedd 构建系统对配方的文件进行检查,并将检查库插入do_fetch任务的签名中。如果修改了任何本地文件,则do_fetch任务和所有依赖于它的任务被重新执行。

默认情况下,所有内容都以具有定义结构的构建目录完成。有关构建目录的其他一般信息,请参阅 Yocto 项目参考手册中的"构建/"部分。

每个配方在构建目录中都有一个区域,未包装的源代码就位于该区域。 S变量指向此区域,用于配方的未包装源代码。任何给定配方的目录名称是从几个不同的变量定义的。上一个数字和以下列表描述了构建目录的层次结构:

  • TMPDIR:开放式构建系统在构建过程中执行所有工作的基础目录。默认基础目录是目录。tmp

  • PACKAGE_ARCH:已构建的包或封装的架构。根据包或包的最终目的地(即机器架构、构建主机、SDK 或特定机器),PACKAGE_ARCH会有所不同。有关详细信息,请参阅该变量的描述。

  • TARGET_OS:目标设备的操作系统。典型的值是"linux"(例如"qemux86-poky-linux")。

  • PN:用于构建包装的配方名称。此变量具有多种含义。但是,在输入文件上下文中使用时,PN表示配方的名称。

  • WORKDIR::开放式构建系统构建配方的位置(即创建包的工作)。

    • PV::用于构建包装的配方版本。

    • PR:用于构建包装的配方的修订。

  • S: 包含给定配方的未包装源文件。

    • BPN:用于构建包装的配方名称。 BPN变量是PN变量的一个版本,但删除了通用前缀和后缀。

    • PV:用于构建包装的配方版本。

注意

在上一个图中,请注意,有两个示例等级:一个基于包架构(即PACKAGE_ARCH),一个基于机器(即机器)。基础结构相同。差异化器是 OpenEmbedd 构建系统用作构建目标(例如一般架构、构建主机、SDK 或特定机器)。

4.3.5.2 Patching

‎取件并拆开源代码后,BitBake 会定位修补文件并将它们应用到源文件中:‎

do_patch任务使用配方的SRC_URI语句和文件路径变量来定位适用的修补程序文件。

修补程序文件的默认处理假定文件有或文件类型。您可以使用SRC_URI参数更改构建系统识别修补程序文件的方式。有关更多信息,请参阅do_patch任务。*.patch*.diff

BitBake 发现并应用多个修补程序,用于单个配方,以它定位修补程序的顺序。文件路径变量定义了构建系统用于搜索修补程序文件的默认目录集。一旦发现,补丁将应用于位于S目录中的配方源文件。

有关源目录创建方式的更多信息,请参阅"源获取"部分。有关如何创建修补程序以及构建系统如何处理修补程序的更多信息,请参阅 Yocto 项目开发任务手册中的"修补代码"部分。您还可以在 Yocto 项目应用程序开发和扩展软件开发套件 (SDK) 手册中看到"使用开发工具修改以修改现有组件的来源"部分,以及 Yocto 项目 Linux 内核开发手册中的"使用传统内核开发来修补内核"部分。

4.3.5.3配置、编译和分期

源代码修补后,BitBake 执行配置和编译源代码的任务。一旦汇编发生,文件被复制到保留区域(阶段),为包装做准备:

构建过程中的此步骤包括以下任务:

  • do_prepare_recipe_sysroot:这项任务在 WORKDIR(即工作地)中设置了两个sysroots 。 并且)以便在包装阶段,sysroot 可以包含包含包含任务的配方所依赖的配方的do_populate_sysroot任务的内容。目标和主机系统运行的本地二进制文件都存在系统根。${}recipe-sysrootrecipe-sysroot-native

  • do_configure:此任务通过启用和禁用正在构建的软件的任何构建时间和配置选项来配置源。配置可以来自配方本身以及继承的类。此外,软件本身可能会根据正在构建的目标进行配置。

    do_configure任务处理的配置特定于配方构建的源代码的配置。

    如果您正在使用autotools 类,您可以使用EXTRA_OECONF或PACKAGECONFIG_CONFARGS变量添加额外的配置选项。有关此变量在该类中如何工作的信息,see the autotools class here.

  • do_compile:一旦完成配置任务,BitBake 将使用do_compile任务编译源。编译发生在B变量指向的目录中。默认情况下,B目录与S目录相同。

  • do_install:汇编完成后,BitBake 执行do_install任务。此任务复制来自 B目录的文件,并将它们放置在D变量指向的保留区域。包装稍后使用此保存目录中的文件进行。

4.3.5.4‎‎包裹拆分‎

‎源代码配置、编译和分阶段后,构建系统分析结果并将输出拆分为包:‎

‎ ‎‎do_package‎‎和‎‎do_packagedata‎‎任务相结合,分析‎‎D‎‎目录中的文件,并根据可用的软件包和文件将其拆分为子集。分析包括以下项目以及其他项目:拆分调试符号、查看包之间的共享库依赖关系以及查看包关系。‎

‎任务根据分析创建包元数据,以便构建系统可以生成最终包。‎‎ ‎‎do_populate_sysroot‎‎任务阶段(副本)‎‎将do_install‎‎任务安装的文件的子集放入适当的 ssroot 中。分析和包拆分过程的工作、分阶段和中间结果使用几个领域:‎do_packagedata

  • ‎ ‎‎PKGD‎‎: 包裹被拆分为单独包之前的目的地目录(即)。‎package

  • ‎ ‎‎PKGDESTWORK‎‎: 任务中用于保存包元数据的临时工作区域( 即 ) 。‎pkgdatado_package

  • ‎ ‎‎PKGDEST:‎‎包裹被拆分后的父目录(即)。‎packages-split

  • ‎ ‎‎PKGDATA_DIR:‎‎一个共享的全球国家目录,保存包装过程中产生的包装元数据。包装过程将元数据从‎‎PKGDESTWORK‎‎复制到‎‎全球可用的PKGDATA_DIR‎‎区域。‎

  • ‎ ‎‎STAGING_DIR_HOST:‎‎构建组件运行的系统系统系统(即)的系统根路径。‎recipe-sysroot

  • ‎ ‎‎STAGING_DIR_NATIVE:‎‎为构建主机构建组件时使用的机根路径(即)。‎recipe-sysroot-native

  • ‎ ‎‎STAGING_DIR_TARGET:‎‎当构建用于在系统上执行的组件并生成另一台机器(例如跨加拿大配方)的代码时,系统根的路径。‎

‎文件‎‎变量定义了在‎‎包‎‎中进入每个包的文件。如果你想要如何做到这一点的细节,你可以看看‎‎包。‎

‎根据正在创建的包类型(RPM、DEB 或‎‎IPK),do_package_write_*‎‎任务创建实际包并将其放置在包源区域(即 。您可以查看"‎‎包馈送‎‎"部分,了解构建过程该部分的更多详细信息。‎${TMPDIR}/deploy

‎注意‎

‎不存在直接从目录创建源的支持。创建此类源通常需要某种源维护机制,以便将新软件包上传到官方包源(例如\ngström 分发)。此功能具有高度分布特定性,因此不会开箱即用。‎deploy/*

4.3.5.5图像生成

一旦包被拆分并存储在包源区域,构建系统使用 BitBake 生成根文件系统图像:

图像生成过程由多个阶段组成,取决于多个任务和变量。 do_rootfs任务为图像创建根文件系统(文件和目录结构)。此任务使用几个关键变量来帮助创建要实际安装的包列表:

  • IMAGE_INSTALL:列出从包装源区域安装的基本包集。

  • PACKAGE_EXCLUDE:指定不应安装到图像中的包。

  • IMAGE_FEATURES: 指定图像中要包含的功能。其中大多数功能映射到用于安装的其他包。

  • PACKAGE_CLASSES:指定用于使用的包后端(例如.RPM、DEB 或 IPK),从而帮助确定在包馈送区域内查找包裹的位置。

  • IMAGE_LINGUAS:确定安装额外语言支持包的语言。

  • PACKAGE_INSTALL:将最终的包裹列表传递给包装经理,以便安装到图像中。

随着IMAGE_ROOTFS指向正在构建的文件系统的位置和提供要安装的软件包最终列表的PACKAGE_INSTALL变量,创建了根文件系统。

包裹安装由包经理控制(例如 dnf/rpm、opkg 或 apt/dpkg),无论是否启用了目标的包管理。在过程结束时,如果目标无法启用包管理,则从根文件系统中删除包管理器的数据文件。作为封装安装最后阶段的一部分,将运行作为封装一部分的安装脚本。当目标系统首次启动时,任何未能在构建主机上运行的脚本都运行在目标上。如果您使用仅读的根文件系统,则所有后安装脚本必须在封装安装阶段的构建主机上成功,因为目标上的根文件系统仅限读取。

任务的最后阶段处理后处理。后处理包括创建一个显性文件和优化。do_rootfs

清单文件()与根文件系统图像位于同一目录中。此文件逐行列出已安装的包。例如,清单文件可用于测试类,以确定是否运行特定测试。有关其他信息,请参阅IMAGE_MANIFEST变量。.manifest

在整个图像中运行的优化过程包括,以及ROOTFS_POSTPROCESS_COMMAND变量定义的任何其他后处理命令。该过程优化了库的大小,而流程优化了共享库的动态链接,以减少可执行库的启动时间。mklibsprelinkmklibsprelink

根文件系统构建后,通过do_image任务开始对图像进行处理。构建系统运行由IMAGE_PREPROCESS_COMMAND变量定义的任何预处理命令。此变量指定在构建系统创建最终图像输出文件之前要调用的功能列表。

构建系统根据IMAGE_FSTYPES变量中指定的图像类型,根据需要动态创建任务。该过程将所有内容转换为图像文件或一组图像文件,并可以压缩根文件系统图像,以减少图像的整体大小。用于根文件系统的格式取决于IMAGE_FSTYPES变量。压缩取决于格式是否支持压缩。do_image_*

例如,创建特定图像类型时动态创建的任务将采取以下形式:

do_image_type

因此,如果IMAGE_FSTYPES指定的类型是动态生成的任务如下:ext4

do_image_ext4

图像创建中涉及的最后任务是do_image_complete任务。此任务通过应用通过IMAGE_POSTPROCESS_COMMAND变量定义的任何图像后处理来完成图像。该变量指定了构建系统创建最终图像输出文件后要调用的功能列表。

注意

整个图像生成过程在伪下运行。在伪下运行确保根文件系统中的文件具有正确的所有权。

4.3.5.6SDK 一代

开放式构建系统使用 BitBake 生成标准 SDK 和可扩展 SDK (eSDK) 的软件开发套件 (SDK) 安装脚本:

注意

有关交叉开发工具链生成的更多信息,请参阅“交叉开发工具链生成”部分。有关使用 do_populate_sdk 任务构建交叉开发工具链时获得的优势的信息,请参阅Yocto 项目应用程序开发和可扩展软件开发工具包 (eSDK) 手册中的“构建 SDK 安装程序”部分。

与图像生成一样,SDK 脚本过程由几个阶段组成,并依赖于许多变量。该 do_populate_sdk 和 do_populate_sdk_ext 任务,用它来帮助这些关键变量创建包的实际安装列表。有关图中列出的变量的信息,请参阅“应用程序开发 SDK ”部分。

do_populate_sdk任务有助于创建标准 SDK 并处理两个部分:目标部分和主机部分。目标部分是为目标硬件构建的部分,包括库和头文件。主机部分是在SDKMACHINE上运行的 SDK 部分 。

do_populate_sdk_ext任务有助于创建可扩展的 SDK,并以不同于其对应部分对标准 SDK 的方式处理主机和目标部分。对于可扩展 SDK,该任务封装了构建系统,其中包括 SDK 所需的一切(主机和目标)。

无论构建的 SDK 类型如何,任务都会执行一些清理工作,然后创建一个交叉开发环境设置脚本和任何所需的配置文件。最终输出是交叉开发工具链安装脚本(.sh文件),其中包括环境设置脚本。

4.3.5.7标记文件和任务的重新运行

对于每个成功完成的任务,BitBake 会在STAMPS_DIR 目录中写入一个戳文件。戳文件的文件名的开头由STAMP变量决定,文件名的结尾由任务名称和当前输入校验和组成。

注意

这个命名方案假设 BB_SIGNATURE_HANDLER 是“OEBasicHash”,这在当前的 OpenEmbedded 中几乎总是如此。

为了确定是否需要重新运行任务,BitBake 检查是否存在具有匹配输入校验和的标记文件。在这种情况下,假定任务的输出存在并且仍然有效。否则,任务将重新运行。

注意

标记机制比“场景任务和共享状态”部分中描述的共享状态(sstate)缓存机制更通用。BitBake 避免重新运行任何具有有效戳文件的任务,而不仅仅是可以通过 sstate 缓存加速的任务。

但是,您应该意识到图章文件仅用作某些工作已完成的标记,并且这些文件不记录任务输出。实际的任务输出通常在TMPDIR中的某处 (例如在某些配方的WORKDIR 中。) sstate 缓存机制添加的是一种缓存任务输出的方法,然后可以在构建机器之间共享。

由于STAMPS_DIR通常是TMPDIR的子目录,删除 TMPDIR也将删除STAMPS_DIR,这意味着将正确地重新运行任务以重新填充TMPDIR。

如果您希望某些任务始终被视为“过时”,您可以使用nostamp varflag对其进行标记。如果其他任务依赖于这样的任务,那么该任务也将始终被视为过时,这可能不是您想要的。

有关如何查看任务签名信息的详细信息,请参阅Yocto 项目开发任务手册中的“查看任务变量依赖关系”部分。

4.3.5.8场景任务和共享状态

到目前为止的任务描述假设 BitBake 需要构建一切,并且不存在可用的预构建对象。如果预建对象可用,BitBake 确实支持跳过任务。这些对象通常以共享状态 (sstate) 缓存的形式提供。

注意

有关影响 sstate 的变量的信息,请参阅 SSTATE_DIR 和 SSTATE_MIRRORS 变量。

setscene 任务(即do_taskname _setscene)的想法是任务的一个版本,BitBake 可以跳到最终结果,并根据需要简单地将一组文件放置到特定位置,而不是构建某些东西。在某些情况下,有一个 setscene 任务变体是有意义的(例如在do_package_write_* 任务中生成包文件 )。在其他情况下,它没有意义(例如 do_patch任务或 do_unpack任务),因为所涉及的工作将等于或大于底层任务。

在构建系统中,具有 setscene 变体的常见任务是 do_package、 do_package_write_*、 do_deploy、 do_packagedata和 do_populate_sysroot。请注意,这些任务代表了其输出是最终结果的大多数任务。

构建系统了解这些任务与其他先前任务之间的关系。例如,如果运行BitBake的 do_populate_sysroot_setscene东西,它没有任何意义运行任何的do_fetchdo_unpackdo_patch, do_configuredo_compile,和do_install任务。但是,如果 do_package需要运行,BitBake 需要运行那些其他任务。

如果一切都可以来自 sstate 缓存,那会变得更加复杂,因为根本不需要某些对象。例如,如果没有要编译或修补的内容,则不需要编译器或本机工具(例如 quilt)。如果do_package_write_*包可以从 sstate 获得,BitBake 不需要do_package任务数据。

为了处理所有这些复杂性,BitBake 分两个阶段运行。首先是“场景”阶段。在此阶段,BitBake 首先检查 sstate 缓存中是否有它计划构建的任何目标。BitBake 会快速检查对象是否存在,而不是进行完整下载。如果什么都不存在,则第二阶段(即场景阶段)完成并继续进行主要构建。

如果在 sstate 缓存中找到对象,构建系统将从用户指定的最终目标向后工作。例如,如果正在构建映像,则构建系统首先查找该映像所需的包以及构建映像所需的工具。如果这些可用,则不需要编译器。因此,甚至没有下载编译器。如果发现某些内容不可用,或者下载或 setscene 任务失败,则构建系统会尝试从缓存中安装依赖项,例如编译器。

sstate 缓存中对象的可用性由BB_HASHCHECK_FUNCTION 变量指定的函数处理,并返回可用对象列表。BB_SETSCENE_DEPVALID 变量指定的函数是确定是否需要遵循给定依赖关系以及是否需要传递任何给定关系的函数。该函数返回 True 或 False 值。

4.3.6图像

构建系统生成的映像是根文件系统的压缩形式,可以在目标设备上启动。您可以从一般工作流程图中看到,BitBake 输出部分由图像组成。本节将仔细查看此输出:

注意

有关 Yocto 项目提供的示例图像列表,请参阅Yocto 项目参考手册中的“图像”一章。

构建过程将图像写入文件夹 内的 构建目录tmp/deploy/images/machine/,如图所示。此文件夹包含预期要加载到目标设备上的任何文件。所述DEPLOY_DIR变量指向deploy目录,而 DEPLOY_DIR_IMAGE 变量指向相应的目录包含用于当前配置的图像。

  • kernel-image:内核二进制文件。该 KERNEL_IMAGETYPE 变量决定了内核映像文件的命名方案。根据此变量,文件可以以各种命名字符串开头。本deploy/images/机目录可以包含计算机的多个图像文件。

  • root-filesystem-image:目标设备的根文件系统(例如 *.ext3*.bz2文件)。所述 IMAGE_FSTYPES 变量确定根文件系统的图像类型。本 deploy/images/机目录可以包含机器多根文件系统。

  • 内核模块:包含为内核构建的所有模块的压缩包。内核模块 tarball 用于遗留目的,可以通过将MODULE_TARBALL_DEPLOY 变量设置为“0”来抑制 。本deploy/images/机目录可以包含机器多内核模块压缩包。

  • 引导加载程序:如果适用于目标机器,支持镜像的引导加载程序。本deploy/images/机目录就可以包含多个设备的引导程序。

  • 符号链接:deploy/images/机器文件夹包含一个符号链接,指向每台机器最近构建的文件。这些链接对于需要获取每个文件的最新版本的外部脚本可能很有用。

4.3.7应用开发SDK

在一般工作流图中,标记为“应用程序开发 SDK”的输出代表一个 SDK。SDK 生成过程因您构建的是可扩展 SDK(例如imagename)还是标准 SDK(例如imagename)而异。本节将仔细查看此输出:bitbake -c populate_sdk_extbitbake -c populate_sdk

此输出的特定形式是一组文件,其中包括自解压 SDK 安装程序 ( *.sh)、主机和目标清单文件以及用于 SDK 测试的文件。当 SDK 安装程序文件运行时,它会安装 SDK。SDK 由一个交叉开发工具链、一组库和头文件以及一个 SDK 环境设置脚本组成。运行此安装程序实质上是设置您的交叉开发环境。您可以将跨工具链视为“主机”部分,因为它运行在 SDK 机器上。您可以将库和头文件视为“目标”部分,因为它们是为目标硬件构建的。添加了环境设置脚本,以便您可以在使用工具之前初始化环境。

注意

  • Yocto 项目支持多种方法,您可以通过这些方法设置此交叉开发环境。这些方法包括下载预构建的 SDK 安装程序或构建和安装您自己的 SDK 安装程序。

  • 有关 Yocto 项目开发环境中交叉开发工具链的背景信息,请参阅“交叉开发工具链生成”部分。

  • 有关设置交叉开发环境的信息,请参阅Yocto 项目应用程序开发和可扩展软件开发工具包 (eSDK)手册。

SDK 的所有输出文件都写入Build Directorydeploy/sdk内的文件夹中,如上图所示。根据 SDK 的类型,有几个变量可以配置这些文件。以下是与可扩展 SDK 关联的变量:

  • DEPLOY_DIR:指向deploy目录。

  • SDK_EXT_TYPE:控制是否将共享状态工件复制到可扩展 SDK 中。默认情况下,所有必需的共享状态工件都被复制到 SDK 中。

  • SDK_INCLUDE_PKGDATA:指定 packagedata 是否包含在“world”目标中所有配方的可扩展 SDK 中。

  • SDK_INCLUDE_TOOLCHAIN:指定在构建可扩展 SDK 时是否包含工具链。

  • SDK_LOCAL_CONF_WHITELIST:允许从构建系统配置到可扩展 SDK 配置的变量列表。

  • SDK_LOCAL_CONF_BLACKLIST:不允许从构建系统配置进入可扩展 SDK 配置的变量列表。

  • SDK_INHERIT_BLACKLIST:要从可扩展 SDK 配置中全局删除的INHERIT值中删除的类列表 。

下一个列表显示了与标准 SDK 关联的变量:

  • DEPLOY_DIR:指向deploy目录。

  • SDKMACHINE:指定运行交叉开发工具以创建目标硬件包的机器的体系结构。

  • SDKIMAGE_FEATURES:列出要包含在 SDK 的“目标”部分中的功能。

  • TOOLCHAIN_HOST_TASK:列出构成 SDK 主机部分(即在SDKMACHINE上运行的部分)的包。当您使用 创建的SDK,一组默认套餐适用。此变量允许您添加更多包。bitbake -c populate_sdk imagename

  • TOOLCHAIN_TARGET_TASK:列出构成 SDK 目标部分的包(即为目标硬件构建的部分)。

  • SDKPATH:定义安装脚本提供的默认 SDK 安装路径。

  • SDK_HOST_MANIFEST:列出构成 SDK 主机部分的所有已安装包。此变量在可扩展 SDK 开发中也起着次要作用。但是,它主要用于标准 SDK。

  • SDK_TARGET_MANIFEST:列出构成 SDK 目标部分的所有已安装包。此变量对于可扩展 SDK 开发也起着次要作用。但是,它主要用于标准 SDK。

4.4交叉开发工具链生成

在创建交叉开发工具链时,Yocto 项目会为您完成大部分工作。本节提供有关如何创建和使用交叉开发工具链的一些技术背景。有关工具链的更多信息,您还可以参阅Yocto 项目应用程序开发和可扩展软件开发工具包 (eSDK)手册。

在 Yocto Project 开发环境中,交叉开发工具链用于构建在目标硬件上运行的图像和应用程序。只需几个命令,OpenEmbedded 构建系统就会为您创建这些必要的工具链。

下图显示了有关工具链构建和使用的高级构建环境。

大多数工作发生在构建主机上。这是用于构建图像的机器,通常在 Yocto 项目环境中工作。当您运行 BitBake以创建映像时,OpenEmbedded 构建系统使用主机gcc编译器来引导名为gcc-cross. 该gcc-cross编译器是什么BitBake的使用编译源文件创建目标图像时。您可以gcc-cross简单地将其视为仅在 BitBake 内部使用的自动生成的交叉编译器。

注意

不使用可扩展 SDK,gcc-cross-canadian 因为此 SDK 提供了 OpenEmbedded 构建系统的副本,并且其中的 sysroot 包含gcc-cross.

引导标准工具链时发生的事件链:

binutils-cross -> linux-libc-headers -> gcc-cross -> libgcc-initial -> glibc -> libgcc -> gcc-runtime

  • gcc: 编译器,GNU Compiler Collection (GCC)。

  • binutils-cross:运行gcc-cross引导操作阶段和构建 C 库头文件所需的二进制实用程序。

  • linux-libc-headers:交叉编译器和 C 库构建所需的头文件。

  • libgcc-initial:引导程序所需的 gcc 支持库的初始版本glibc

  • libgcc: gcc 支持库的最终版本,只有在有 C 库要链接时才能构建。

  • glibc: GNU C 库。

  • gcc-cross:交叉编译器引导过程的最后阶段。此阶段生成 BitBake 在为目标设备构建映像时使用的实际交叉编译器。

    这个工具是一个“本地”工具(即它被设计为在构建主机上运行)。

  • gcc-runtime:由工具链引导过程产生的运行时库。此工具生成一个二进制文件,其中包含目标设备所需的运行时库。

您可以使用 OpenEmbedded 构建系统为用于开发应用程序的可重定位 SDK 构建安装程序。当您运行安装程序时,它会安装工具链,其中包含开发工具(例如 、gcc-cross-canadianbinutils-cross-canadian和其他nativesdk-*工具),这些工具是 SDK 原生的(即SDK_ARCH原生的),您需要交叉编译和测试您的软件. 该图显示了您用来轻松构建此工具链的命令。这个交叉开发工具链是为在SDKMACHINE上执行而构建的,它可能与构建主机在同一台机器上 ,也可能不同。

注意

如果 Yocto 项目支持您的目标架构,您可以利用 Yocto 项目附带的预构建映像,并且已经包含交叉开发工具链安装程序。

以下是可重定位工具链的引导过程:

gcc -> binutils-crosssdk -> gcc-crosssdk-initial -> linux-libc-headers -> glibc-initial -> nativesdk-glibc -> gcc-crosssdk -> gcc-cross-canadian

  • gcc:构建主机的 GNU 编译器集合 (GCC)。

  • binutils-crosssdk:运行gcc-crosssdk-initial引导操作阶段所需的最低限度的二进制实用程序。

  • gcc-crosssdk-initial:创建交叉编译器的引导过程的早期阶段。这个阶段构建了足够多的 gcc-crosssdk支持部分,以便引导过程的最后阶段可以生成最终的交叉编译器。此工具是在构建主机上运行的“本机”二进制文件。

  • linux-libc-headers: 交叉编译器所需的头文件。

  • glibc-initial:引导程序所需的嵌入式 GLIBC 的初始版本nativesdk-glibc

  • nativesdk-glibc:嵌入式 GLIBC 需要引导 gcc-crosssdk.

  • gcc-crosssdk:可重定位交叉编译器的引导过程的最后阶段。这gcc-crosssdk是一个暂时的编译器,永远不会离开构建主机。其目的是在引导过程中帮助创建gcc-cross-canadian 可重定位的最终编译器。这个工具也是一个“本地”包(即它被设计为在构建主机上运行)。

  • gcc-cross-canadian: 最终的可重定位交叉编译器。在SDKMACHINE上运行时,此工具会生成在目标设备上运行的可执行代码。每个架构只生成一个跨加拿大编译器,因为它们可以使用通过编译命令传递给编译器的配置针对不同的处理器优化。这避免了对多个编译器的需求,从而减少了工具链的大小。

注意

有关构建交叉开发工具链安装程序时获得的优势的信息,请参阅Yocto 项目应用程序开发和可扩展软件开发工具包 (eSDK) 手册中的“构建 SDK 安装程序”附录。

4.5共享状态缓存

按照设计,OpenEmbedded 构建系统从头开始构建所有内容,除非BitBake可以确定不需要重新构建部分。从根本上说,从头开始构建很有吸引力,因为这意味着所有部件都是全新构建的,并且不可能出现可能导致问题的陈旧数据。当开发人员遇到问题时,他们通常会默认从头开始构建,因此他们从一开始就知道状态。

从头开始构建图像对这个过程来说既是优点也是缺点。如上一段所述,从头开始构建可确保一切都是最新的并从已知状态开始。然而,从头开始构建也需要更长的时间,因为它通常意味着重建不一定需要重建的东西。

Yocto 项目实现了支持增量构建的共享状态代码。共享状态代码的实现回答了以下问题,这些问题是 OpenEmbedded 增量构建支持系统中的基本障碍:

  • 系统的哪些部分发生了变化,哪些部分没有发生变化?

  • 如何删除和替换更改的软件?

  • 不需要重新构建的预构建组件在可用时如何使用?

对于第一个问题,构建系统通过创建任务输入的校验和(或签名)来检测给定任务“输入”的变化。如果校验和发生变化,系统会假设输入发生了变化,需要重新运行任务。对于第二个问题,共享状态 (sstate) 代码跟踪哪些任务将哪些输出添加到构建过程。这意味着可以删除、升级或以其他方式操纵给定任务的输出。第三个问题部分由第二个问题的解决方案解决,假设构建系统可以从远程位置获取 sstate 对象并在它们被认为有效时安装它们。

注意

  • 构建系统不会将PR信息作为共享状态包的一部分进行维护 。因此,存在影响维护共享状态提要的考虑因素。有关构建系统如何处理包以及跟踪PR 信息递增的信息,请参阅Yocto 项目开发任务手册中的“自动递增包版本号”部分。

  • 支持增量构建的构建系统中的代码并不是简单的代码。有关帮助您解决与共享状态代码相关的问题的技术,请参阅Yocto 项目开发中的“查看用于创建共享状态任务的输入签名的元数据”和“使共享状态无效以强制运行任务”部分任务手册。

本节的其余部分详细介绍了整体增量构建架构、校验和(签名)和共享状态。

4.5.1总体架构

在确定需要构建系统的哪些部分时,BitBake 基于每个任务而不是每个配方工作。您可能想知道为什么使用每个任务的基础比每个食谱的基础更受欢迎。为了帮助解释,请考虑启用 IPK 打包后端,然后切换到 DEB。在这种情况下, do_install和 do_package任务输出仍然有效。但是,对于每个配方的方法,构建将不包括.deb文件。因此,您必须使整个构建无效并重新运行它。重新运行一切并不是最好的解决方案。此外,在这种情况下,核心必须“教”很多关于特定任务的知识。这种方法不能很好地扩展,并且不允许用户在不接触打包的暂存核心的情况下轻松地在层中添加新任务或作为外部配方添加新任务。

4.5.2校验和(签名)

共享状态代码使用校验和(任务输入的唯一签名)来确定是否需要再次运行任务。由于触发重新运行的是任务输入的更改,因此流程需要检测给定任务的所有输入。对于 shell 任务,事实证明这相当容易,因为构建过程会为每个任务生成一个“运行”shell 脚本,并且可以创建一个校验和,让您很好地了解任务的数据何时发生变化。

使问题复杂化的是,有些内容不应包含在校验和中。首先,存在给定任务的实际特定构建路径 - WORKDIR。工作目录是否更改并不重要,因为它不应该影响目标包的输出。此外,构建过程的目标是使本机或跨包可重定位。

注意

本机和交叉包都在构建主机上运行。但是,交叉包会为目标架构生成输出。

因此校验和需要排除WORKDIR。排除工作目录的简单方法是将WORKDIR设置为某个固定值并为“运行”脚本创建校验和。

另一个问题来自“运行”脚本,其中包含可能会或可能不会被调用的函数。增量构建解决方案包含计算 shell 函数之间依赖关系的代码。此代码用于将“运行”脚本修剪到最小集,从而缓解此问题并使“运行”脚本更具可读性作为奖励。

到目前为止,有针对shell脚本的解决方案。Python 任务呢?即使这些任务更加困难,同样的方法也适用。该过程需要弄清楚 Python 函数访问哪些变量以及它调用哪些函数。同样,增量构建解决方案包含的代码首先计算变量和函数的依赖关系,然后为用作任务输入的数据创建校验和。

与WORKDIR情况一样,可能存在应忽略依赖项的情况。对于这些情况,您可以使用如下所示的行指示构建过程忽略依赖项:

PACKAGE_ARCHS[vardepsexclude] = "MACHINE"

此示例确保PACKAGE_ARCHS变量不依赖于MACHINE的值,即使它确实引用了它。

同样,在某些情况下,您需要添加 BitBake 无法找到的依赖项。您可以使用如下所示的行来完成此操作:

PACKAGE_ARCHS[vardeps] = "MACHINE"

此示例显式添加MACHINE变量作为PACKAGE_ARCHS的依赖项。

例如,考虑使用内联 Python 的情况,其中 BitBake 无法确定依赖项。在调试模式下运行时(即使用 -DDD),BitBake 在发现无法确定其依赖关系的东西时产生输出。Yocto 项目团队目前尚未设法详细涵盖这些依赖项,并且意识到需要解决这种情况。

到目前为止,本节的讨论仅限于对任务的直接输入。基于直接输入的信息在代码中被称为“basehash”。然而,任务的间接输入的问题仍然存在——项目已经构建并存在于 构建目录中。特定任务的校验和(或签名)需要添加特定任务所依赖的所有任务的哈希值。选择要添加的依赖项是一项策略决定。但是,其效果是生成一个主校验和,该校验和结合了 basehash 和任务依赖项的哈希。

在代码级别,有多种方式可以影响 basehash 和相关任务哈希。在 BitBake 配置文件中,您可以为 BitBake 提供一些额外信息来帮助它构建 basehash。以下语句有效地生成了一个全局变量依赖项排除列表(即变量从不包含在任何校验和中):

BB_HASHBASE_WHITELIST ?= "TMPDIR FILE PATH PWD BB_TASKHASH BBPATH DL_DIR \\SSTATE_DIR THISDIR FILESEXTRAPATHS FILE_DIRNAME HOME LOGNAME SHELL TERM \\USER FILESPATH STAGING_DIR_HOST STAGING_DIR_TARGET COREBASE PRSERV_HOST \\PRSERV_DUMPDIR PRSERV_DUMPFILE PRSERV_LOCKDOWN PARALLEL_MAKE \\CCACHE_DIR EXTERNAL_TOOLCHAIN CCACHE CCACHE_DISABLE LICENSE_PATH SDKPKGSUFFIX"

前面的示例不包括 WORKDIR,因为该变量实际上是作为TMPDIR 中的路径构建的,该路径位于 白名单中。

决定通过依赖链包含哪些依赖任务的哈希的规则更复杂,通常使用 Python 函数完成。中的代码 meta/lib/oe/sstatesig.py显示了这方面的两个示例,还说明了如何在需要时将自己的策略插入系统。该文件定义了OpenEmbedded-Core (OE-Core)使用的两个基本签名生成器 :“OEBasic”和“OEBasicHash”。默认情况下,在 BitBake 中启用了一个虚拟的“noop”签名处理程序。这意味着行为与以前的版本没有变化。默认情况下,OE-Core 通过bitbake.conf文件中的此设置使用“OEBasicHash”签名处理程序:

BB_SIGNATURE_HANDLER ?= "OEBasicHash"

“OEBasicHash” BB_SIGNATURE_HANDLER与“OEBasic”版本相同,但将任务哈希添加到图章文件中。这会导致更改任务哈希的任何元数据更改,自动导致任务再次运行。这消除了增加PR值的需要 ,并且对元数据的更改会在整个构建过程中自动波动。

还值得注意的是,这些签名生成器的最终结果是为构建提供一些依赖和哈希信息。这些信息包括:

  • BB_BASEHASH:task-任务名称:配方中每个任务的基本哈希值。

  • BB_BASEHASH_文件名:任务名:每个依赖任务的基本哈希值。

  • BB_TASKHASH:当前正在运行的任务的哈希值。

4.5.3共享状态

如上一节所述,校验和和依赖关系解决了支持共享状态的一半问题。问题的另一半是能够在构建期间使用校验和信息,并能够重用或重建特定组件。

该sstate类是相对通用的实现,如何“捕获”给定任务的快照。这个想法是构建过程不关心任务输出的来源。输出可以是新构建的,也可以从某个地方下载和解压缩。换句话说,构建过程不需要担心它的起源。

存在两种类型的输出。一种类型是在WORKDIR 中创建一个目录。一个很好的例子是do_install或 do_package的输出 。当一组数据合并到共享目录树(例如 sysroot)中时,会出现另一种类型的输出。

Yocto 项目团队试图将实现的细节隐藏在sstate课堂中。从用户的角度来看,向任务添加共享状态包装就像这个来自deploy类的do_deploy示例一样简单 :

DEPLOYDIR = "${WORKDIR}/deploy-${PN}"
SSTATETASKS += "do_deploy"
do_deploy[sstate-inputdirs] = "${DEPLOYDIR}"
do_deploy[sstate-outputdirs] = "${DEPLOY_DIR_IMAGE}"python do_deploy_setscene () {sstate_setscene(d)
}
addtask do_deploy_setscene
do_deploy[dirs] = "${DEPLOYDIR} ${B}"
do_deploy[stamp-extra-info] = "${MACHINE_ARCH}"

以下列表解释了前面的示例:

  • 添加“do_deploy”,在do_deploy任务的前后SSTATETASKS添加一些需要的sstate相关的处理,在sstate类中 实现 。

  • 该声明 将它的输出时,正常运行时(即不使用sstate缓存)。此输出成为共享状态缓存的输入。do_deploy[sstate-inputdirs] = "${DEPLOYDIR}"do_deploy${DEPLOYDIR}

  • 该行导致共享状态缓存的内容被复制到 .do_deploy[sstate-outputdirs] = "${DEPLOY_DIR_IMAGE}"${DEPLOY_DIR_IMAGE}

    注意

    如果do_deploy尚未在共享状态缓存中,或者其输入校验和(签名)从缓存输出时开始发生变化,则任务运行以填充共享状态缓存,然后将共享状态缓存的内容复制到 ${ DEPLOY_DIR_IMAGE }。如果 do_deploy在共享状态缓存中并且它的签名表明缓存的输出仍然有效(即如果没有相关的任务输入发生变化),则共享状态缓存的内容由任务直接复制到 ${ DEPLOY_DIR_IMAGE } ,do_deploy_setscene而不是跳过该do_deploy任务。

  • 以下任务定义是使之前的设置生效所需的粘合逻辑:

    python do_deploy_setscene () {sstate_setscene(d)
    }
    addtask do_deploy_setscene
    

sstate_setscene()将上述标志作为输入,并do_deploy在可能的情况下通过共享状态缓存加速任务。如果任务被加速,则sstate_setscene()返回 True。否则返回False,正常do_deploy任务运行。有关更多信息,请参阅BitBake 用户手册中的“ Setscene ”部分。

  • 该行在任务运行之前创建 和,并将当前工作目录设置为。有关更多信息,请参阅BitBake 用户手册中的“变量标志”部分。do_deploy[dirs] = "${DEPLOYDIR} ${B}"${DEPLOYDIR}${B}do_deploydo_deploy${B}

    注意

    sstate-inputdirssstate-outputdirs相同的情况下,您可以使用sstate-plaindirs. 例如,要保留任务的 ${ PKGD } 和 ${ PKGDEST } 输出do_package ,请使用以下命令:

    do_package[sstate-plaindirs] = "${PKGD} ${PKGDEST}"
    

  • 该行将额外的元数据附加到图章文件。在这种情况下,元数据使任务特定于机器的架构。有关该标志的更多信息,请参阅BitBake 用户手册中的“任务列表”部分 。do_deploy[stamp-extra-info] = "${MACHINE_ARCH}"stamp-extra-info

  • sstate-inputdirs并且sstate-outputdirs还可以与多个目录中。例如,以下声明 PKGDESTWORK和SHLIBWORK为共享状态输入的目录,其填充共享状态的高速缓存,以及PKGDATA_DIR和 SHLIBSDIR作为相应的共享状态的输出目录:

    do_package[sstate-inputdirs] = "${PKGDESTWORK} ${SHLIBSWORKDIR}"
    do_package[sstate-outputdirs] = "${PKGDATA_DIR} ${SHLIBSDIR}"
    

  • 这些方法还包括在操作共享状态目录结构时获取锁文件的能力,用于文件添加或删除敏感的情况:

    do_package[sstate-lockfile] = "${PACKAGELOCK}"
    

在幕后,共享状态代码通过在 SSTATE_DIR和 SSTATE_MIRRORS 中查找共享状态文件来工作。下面是一个例子:

SSTATE_MIRRORS ?= "\file://.\* http://someserver.tld/share/sstate/PATH;downloadfilename=PATH \n \file://.\* file:///some/local/dir/sstate/PATH"

注意

共享状态目录 ( SSTATE_DIR ) 被组织成两个字符的子目录,其中子目录名称基于散列的前两个字符。如果镜像的共享状态目录结构与SSTATE_DIR具有相同的结构,则必须指定“PATH”作为 URI 的一部分,以使构建系统能够映射到适当的子目录。

共享状态包的有效性可以通过查看文件名来检测,因为文件名包含本节前面描述的任务校验和(或签名)。如果找到有效的共享状态包,构建过程会下载它并使用它来加速任务。

构建过程使用*_setscene任务加速阶段的任务。BitBake 在主执行代码之前经历这个阶段,并尝试加速任何可以找到共享状态包的任务。如果任务的共享状态包可用,则使用共享状态包。这意味着不执行任务和它所依赖的任何任务。

作为一个现实世界的例子,目标是在构建基于 IPK 的图像时,只有 do_package_write_ipk 任务才能获取和提取它们的共享状态包。由于未使用 sysroot,它永远不会被提取。这是基于任务的方法优于基于配方的方法的另一个原因,后者必须安装每个任务的输出。

4.6自动添加运行时依赖

OpenEmbedded 构建系统会自动在包之间添加常见类型的运行时依赖项,这意味着您无需使用RDEPENDS显式声明包 。有三种自动机制(shlibdepspcdepsdepchains)分别处理共享库、包配置 (pkg-config) 模块 -dev-dbg包。对于其他类型的运行时依赖项,您必须手动声明依赖项。

  • shlibdeps:在每个recipe的 do_package任务中,都会定位到recipe安装的所有共享库。对于每个共享库,包含共享库的包被注册为提供共享库。更具体地说,该包被注册为提供 库的 soname。生成的共享库到包映射由 do_packagedata 任务全局保存在 PKGDATA_DIR 中。

    同时,检查配方安装的所有可执行文件和共享库,以查看它们链接到哪些共享库。对于找到的每个共享库依赖项,查询PKGDATA_DIR以查看某个包(可能来自不同的配方)是否包含共享库。如果找到这样的包,则将运行时依赖项从依赖于共享库的包添加到包含该库的包。

    自动添加的运行时依赖项还包括版本限制。此版本限制指定至少必须使用提供共享库的包的当前版本,就好像“包(> = 版本)”已添加到RDEPENDS 一样。如果需要,这会在安装依赖于共享库的包时强制升级包含共享库的包。

    如果您想避免将包注册为提供特定共享库(例如,因为该库仅供内部使用),则将该库添加到 包配方中的PRIVATE_LIBS 中。

  • pcdeps:在do_package每个recipe的任务期间,recipe*.pc安装的所有pkg-config模块(文件)都被定位。对于每个模块,包含该模块的包被注册为提供该模块。生成的模块到包的映射由 任务全局保存在PKGDATA_DIR 中do_packagedata

    同时,对配方安装的所有 pkg​​-config 模块进行检查,以查看它们所依赖的其他 pkg-config 模块。如果一个模块包含指定另一个模块的“Requires:”行,则该模块被视为依赖于另一个模块。对于每个模块依赖项,查询PKGDATA_DIR以查看某个包是否包含该模块。如果找到这样的包,则将运行时依赖项从依赖于该模块的包添加到包含该模块的包。

    注意

    pcdeps 机制最常推断 -dev 包之间的依赖关系。

  • depchains: 如果一个包foo依赖于一个包bar,那么foo-devfoo-dbg也分别依赖于 bar-devbar-dbg。以-dev 包为例,bar-dev包可能提供 所需的头文件和共享库符号链接foo-dev,这表明包之间需要依赖关系。

    添加的依赖项采用RRECOMMENDSdepchains的形式 。

    注意

    默认情况下,对foo-dev也有RDEPENDS样式的依赖 foo,因为RDEPENDS:${PN}-dev(在 bitbake.conf 中设置)的默认值包括“${PN}”。

    确保依赖链永远不会中断,-dev并且 -dbg默认情况下始终生成包,即使包是空的。有关更多信息,请参阅 ALLOW_EMPTY变量。

do_package任务依赖于do_packagedata在每个配方的任务DEPENDS通过使用的[deptask] 声明,这保证了所需的,只要当所要求的共享库/模块到包映射信息将是可用的DEPENDS已正确设置。

4.7 Fakeroot 和 Pseudo

当允许执行通常为 root 用户保留的某些操作(例如do_install、 do_package_write*、 do_rootfs和 do_image*)时,某些任务更容易实现 。例如,该do_install任务受益于能够将已安装文件的 UID 和 GID 设置为任意值。

允许任务仅执行 root 操作的一种方法是要求BitBake以 root 身份运行。但是这种方法比较麻烦,而且存在安全问题。实际使用的方法是在“假”root 环境中运行受益于root 权限的任务。在此环境中,任务及其子进程认为它们以 root 用户身份运行,并看到文件系统的内部一致视图。只要生成最终输出(例如包或图像)不需要 root 权限,一些早期步骤在假 root 环境中运行的事实不会导致问题。

在伪根环境中运行任务的能力被称为“ fakeroot ”,它源自 BitBake 关键字/变量标志,为任务请求伪根环境。

在OpenEmbedded Build System 中,实现 fakeroot 的程序称为Pseudo。使用环境变量伪覆盖系统调用LD_PRELOAD,导致以root身份运行的错觉。为了跟踪需要 root 权限的操作产生的“假”文件所有权和权限,Pseudo 使用了 SQLite 3 数据库。该数据库存储在 ${WORKDIR 中,}/pseudo/files.db 用于单个配方。将数据库存储在文件中而不是内存中可以在任务和构建之间提供持久性,这是使用 fakeroot 无法实现的。

注意

如果您添加自己的任务来操作与 fakeroot 任务相同的文件或目录,那么该任务也需要在 fakeroot 下运行。否则,该任务无法运行仅限 root 的操作,也无法看到其他任务设置的虚假文件所有权和权限。您还需要添加对 的依赖 virtual/fakeroot-native:do_populate_sysroot,给出以下内容:

fakeroot do_mytask () {...
}
do_mytask[depends] += "virtual/fakeroot-native:do_populate_sysroot"

有关更多信息,请参阅BitBake 用户手册中的 FAKEROOT*变量。您还可以参考“为什么不是 Fakeroot?”有关 Fakeroot 和 Pseudo 背景信息的文章。

4.Yocto项目概念相关推荐

  1. 2设置使用 Yocto 项目

    2设置使用 Yocto 项目 目录 2设置使用 Yocto 项目 2.1创建团队开发环境 2.2准备构建主机 2.2.1 搭建原生 Linux 主机 2.2.2设置使用 CROss 平台(CROPS) ...

  2. YOCTO项目介绍:通过提供模版、工具和方法帮助开发者创建基于linux内核的定制系统

    目录 YOCTO项目介绍 配置内核 build配套 Yocto ,是一个开源社区.它通过提供模版.工具和方法帮助开发者创建基于linux内核的定制系统,支持ARM, PPC, MIPS, x86 (3 ...

  3. 利用Yocto构建嵌入式Linux教程01--第一个Yocto项目构建

    大家好,从今日开始,计划写一个利用Yocto构建嵌入式Linux的教程,算是对个人工作和学习的一个总结. 本教程选用的Yocto版本为3.0.4,我使用的Linux发行版为Ubuntu 18.04 ( ...

  4. # 行动、任务、项目概念区分

    行动.任务.项目概念区分 1.行动(todo或action) 行动就是确定时间节点,可以立即去做的事情.行动容易操作和衡量. 2.任务(task) 任务通常指所接受的工作,所担负的职责,是指为了完成某 ...

  5. 天嵌TQ_E9卡片电脑移植飞思卡尔yocto L4.1.15_1.0.0_ga 第一篇 yocto项目建立

    本移植过程参考飞思卡尔的Freescale_Yocto_Project_User's_Guide.pdf文档,请自行到飞思卡尔下载fsl-yocto-L4.1.15_1.0.0-ga.zip文件夹. ...

  6. BeagleBone 实施 Yocto 项目

    特点 Yocto 项目生产工具和流程,支持为嵌入式软件创建 Linux 发行版,独立于架构. BeagleBone Black 是一个平台,允许用户根据自己的喜好快速轻松地执行安装和自定义 从 Yoc ...

  7. 构建YOCTO项目详细教程

    系统要求 最少 4-8 GB 内存 磁盘剩余空间至少 60-80 GB CentOS 7.6 或者其他支持Linux发行版 安装软件依赖( CentOS-7): sudo yum install -y ...

  8. i.MX Yocto项目用户指南 -- 下

    i.MX Yocto项目用户指南 – 下 5映像构建 本节提供了构建映像的详细信息和过程. 5.1构建配置 i. MX提供了一个脚本fsl-setup-release.sh,它简化了i.MX机器的设置 ...

  9. Yocto基本概念及介绍

    Yocto详解 参考:http://www.yoctoproject.org/docs/2.1/mega-manual/mega-manual.html#creating-a-general-laye ...

最新文章

  1. Debian 6.0 安装过程 及中文乱码
  2. 【Elasticsearch】第2篇:Elasticsearch分布式安装
  3. uniapp的目录结构反思与整理 app.vue【base】pages.json【配置】main.json【框架入口文件】
  4. 温故之 “插入排序”
  5. 苹果新品又要来了 下周可能推出AirPods Studio
  6. _临武县组合式桥梁伸缩缝F型伸缩缝—批发
  7. 欣赏下国外人css3打造的载入动画
  8. 登录mysql 1130_解决远程登录mysql数据库报1130错误-阿里云开发者社区
  9. CUDA环境变量添加
  10. java messagebox_由MessageBox透视Win32 API的调用 | 学步园
  11. Android性能优化典范-第2季
  12. 读取金税盘数据库_一种基于金税盘控制系统登录和数据同步的方法与流程
  13. win10 动态磁盘 linux,windows10系统下基本磁盘变成动态磁盘了如何解决
  14. [笔记分享] [SD] msm8926 sd 探测流程
  15. 论文阅读-Face X-ray for More General Face Forgery Detection
  16. 2009年毕业设计题目:网上自助装机系统的设计与实现
  17. Chromium网页CPU光栅化原理分析
  18. PHP生成压缩包 (并下载)【解决压缩包下载,提示压缩包损坏】
  19. 什么是AUTOSAR, 为什么要用AUTOSAR
  20. tomcat修改配置文件ip为服务器真实ip

热门文章

  1. 针对部分16系显卡通过VS2017编译的YOLOV3测试成功但图像无检测框的问题:
  2. 梦断代码 ---阅读笔记02
  3. 图像处理的一些相关知识(Related knowledge for IQA)
  4. 账号被罚了,申诉的结果出来了,果然
  5. js解决浏览器,SpeechSynthesis不能正常合成中文语音
  6. 【web自动化测试Robotframework开发手册—特殊元素】
  7. 新技术的福音:瘫痪者也能用眼睛写“微博”
  8. dellr420部署os_Dell R420 RAID建立以及系统安装
  9. 一位资深开发的个人经历 【转自百度贴吧 java吧 原标题 4年java 3年产品 现在又开始做android了】...
  10. JavaScript - 语言进阶