Buildroot 用户手册 (中文)

2022-11-01 14:57:23 浏览数 (1)

大家好,又见面了,我是你们的朋友全栈君。

文章目录

  • I. Getting started
    • 1. About Buildroot
    • 2. System requirements
      • 2.1. Mandatory packages
      • 2.2. Optional packages
    • 3. Getting Buildroot
    • 4. Buildroot quick start
      • 4.1 configuration
      • 4.2 build
    • 5. Community resources
  • II. User guide
    • 6. Buildroot configuration
      • 6.1. Cross-compilation toolchain
        • 6.1.1. Internal toolchain backend
        • 6.1.2. External toolchain backend
        • 6.1.3. Build an external toolchain with Buildroot
        • 6.1.4. External toolchain wrapper
      • 6.2. /dev management
      • 6.3. init system
    • 7. Configuration of other components
    • 8. General Buildroot usage
      • 8.1. make tips
      • 8.2. Understanding when a full rebuild is necessary
      • 8.3. Understanding how to rebuild packages
      • 8.4. Offline builds
      • 8.5. Building out-of-tree
      • 8.6. Environment variables
      • 8.7. Dealing efficiently with filesystem images
      • 8.8. Details about packages
      • 8.9. Graphing the dependencies between packages
      • 8.10. Graphing the build duration
      • 8.11. Graphing the filesystem size contribution of packages
      • 8.12. Top-level parallel build
      • 8.13. Integration with Eclipse
      • 8.14. Advanced usage
        • 8.14.1 Using the generated toolchain outside Buildroot
        • 8.14.2 Using `gdb` in Buildroot
        • 8.14.3 Using `ccache` in Buildroot
        • 8.14.4 Location of downloaded packages
        • 8.14.5 Package-specific make targets
        • 8.14.6 Using Buildroot during development
    • 9. Project-specific customization
      • 9.1. Recommended directory structure
        • 9.1.1. Implementing layered customizations
      • 9.2. Keeping customizations outside of Buildroot
        • 9.2.1. Layout of a br2-external tree
      • 9.3. Storing the Buildroot configuration
      • 9.4. Storing the configuration of other components
      • 9.5. Customizing the generated target filesystem
        • 9.5.1. Setting file permissions and ownership and adding custom devices nodes
      • 9.6. Adding custom user accounts
      • 9.7. Customization after the images have been created
      • 9.8. Adding project-specific patches
      • 9.9. Adding project-specific packages
      • 9.10. Quick guide to storing your project-specific customizations
    • 10. Using SELinux in Buildroot
      • 10.1. Enabling SELinux support
      • 10.2. SELinux policy tweaking
    • 11. Frequently Asked Questions & Troubleshooting
      • 11.1. The boot hangs after Starting network…
      • 11.2. Why is there no compiler on the target?
      • 11.3. Why are there no development files on the target?
      • 11.4. Why is there no documentation on the target?
      • 11.5. Why are some packages not visible in the Buildroot config menu?
      • 11.6. Why not use the target directory as a chroot directory?
      • 11.7. Why doesn’t Buildroot generate binary packages (.deb, .ipkg…)?
      • 11.8. How to speed-up the build process?
    • 12. Known issues
    • 13. Legal notice and licensing
      • 13.1. Complying with open source licenses
      • 13.2. Complying with the Buildroot license
        • 13.2.1. Patches to packages
    • 14. Beyond Buildroot
      • 14.1. Boot the generated images
        • 14.1.1. NFS boot
        • 14.1.2. Live CD
      • 14.2. Chroot
  • III. Developer guide
    • 15. How Buildroot works
    • 16. Coding style
      • 16.1. Config.in file
      • 16.2. The .mk file
      • 16.3. The documentation
      • 16.4. Support scripts
    • 17. Adding support for a particular board
    • 18. Adding new packages to Buildroot
      • 18.1. Package directory
      • 18.2. Config files
        • 18.2.1. `Config.in` file
        • 18.2.2. `Config.in.host` file
        • 18.2.3. Choosing `depends on` or `select`
        • 18.2.4. Dependencies on target and toolchain options
        • 18.2.5. Dependencies on a Linux kernel built by buildroot
        • 18.2.6. Dependencies on udev /dev management
        • 18.2.7. Dependencies on features provided by virtual packages
      • 18.3. The .mk file
      • 18.4. The .hash file
      • 18.5. Infrastructure for packages with specific build systems
        • 18.5.1. `generic-package` tutorial
        • 18.5.2. `generic-package` reference
      • 18.6. Infrastructure for autotools-based packages
        • 18.6.1. `autotools-package` tutorial
        • 18.6.2. `autotools-package` reference
      • 18.7. Infrastructure for CMake-based packages
      • 18.8. Infrastructure for Python packages
      • 18.9. Infrastructure for LuaRocks-based packages
      • 18.10. Infrastructure for Perl/CPAN packages
      • 18.11. Infrastructure for virtual packages
      • 18.12. Infrastructure for packages using kconfig for configuration files
      • 18.13. Infrastructure for rebar-based packages
      • 18.14. Infrastructure for Waf-based packages
      • 18.15. Infrastructure for Meson-based packages
      • 18.16. Integration of Cargo-based packages
      • 18.17. Infrastructure for Go packages
      • 18.18. Infrastructure for QMake-based packages
      • 18.19. Infrastructure for packages building kernel modules
      • 18.20. Infrastructure for asciidoc documents
      • 18.21. Infrastructure specific to the Linux kernel package
        • 18.21.1. linux-kernel-tools
        • 18.21.2. linux-kernel-extensions
      • 18.22. Hooks available in the various build steps
        • 18.22.1. Using the POST_RSYNC hook
        • 18.22.2. Target-finalize hook
      • 18.23. Gettext integration and interaction with packages
      • 18.24. Tips and tricks
        • 18.24.1. Package name, config entry name and makefile variable relationship
        • 18.24.2. How to check the coding style
        • 18.24.3. How to test your package
        • 18.24.4. How to add a package from GitHub
        • 18.24.5. How to add a package from Gitlab
      • 18.25. Conclusion
    • 19. Patching a package
      • 19.1. Providing patches
        • 19.1.1. Downloaded
        • 19.1.2. Within Buildroot
        • 19.1.3. Global patch directory
      • 19.2. How patches are applied
      • 19.3. Format and licensing of the package patches
      • 19.4. Integrating patches found on the Web
    • 20. Download infrastructure
    • 21. Debugging Buildroot
    • 22. Contributing to Buildroot
      • 22.1. Reproducing, analyzing and fixing bugs
      • 22.2. Analyzing and fixing autobuild failures
      • 22.3. Reviewing and testing patches
      • 22.4. Work on items from the TODO list
      • 22.5. Submitting patches
      • 22.6. Reporting issues/bugs or getting help
      • 22.7. Using the run-tests framework
    • 23. DEVELOPERS file and get-developers
    • 24. Release Engineering
      • 24.1. Releases
      • 24.2. Development
  • IV. Appendix
    • 25. Makedev syntax documentation
    • 26. Makeusers syntax documentation
    • 27. Migrating from older Buildroot versions
      • 27.1. Migrating to 2016.11
      • 27.2. Migrating to 2017.08

本文为译文,英文原文地址:The Buildroot user manual

I. Getting started

1. About Buildroot

Buildroot是一个工具,它使用交叉编译简化了为嵌入式系统构建完整Linux系统的过程,并实现了自动化。

为了实现这一点,Buildroot能够为您的目标生成交叉编译工具链( a cross-compilation toolchain)、根文件系统(a root filesystem)、Linux内核映像(a Linux kernel image)和引导加载程序(a bootloader)。Buildroot可以独立地用于这些选项的任何组合(例如,您可以使用现有的交叉编译工具链,只用Buildroot构建您的根文件系统)。

Buildroot主要适用于使用嵌入式系统的人。嵌入式系统通常使用的处理器不是每个人都习惯在个人电脑中使用的常规x86处理器。它们可以是PowerPC处理器,MIPS处理器,ARM处理器等。

Buildroot支持许多处理器及其变体;它还提供了几种现成电路板的默认配置。除此之外,很多第三方项目都是基于,或者在Buildroot之上开发他们的BSP[1]或SDK[2]。

2. System requirements

Buildroot设计用于在Linux系统上运行。

虽然Buildroot本身将构建它编译所需的大多数主机包,但某些标准的Linux实用程序预计已经安装在主机系统上。下面是强制包和可选包的概述(注意,不同发行版的包名称可能有所不同)。

2.1. Mandatory packages

以下是 Linux 环境上必须安装的程序:

代码语言:javascript复制
// Build tools:
which
sed
make (version 3.81 or any later)
binutils
build-essential (only for Debian based systems)
gcc (version 4.8 or any later)
g   (version 4.8 or any later)
bash
patch
gzip
bzip2
perl (version 5.8.7 or any later)
tar
cpio
unzip
rsync
file (must be in /usr/bin/file)
bc

//Source fetching tools:
wget

2.2. Optional packages

以下是可选安装的程序:

  • Recommended dependencies:

Buildroot中的一些特性或实用程序,如the legal-infothe graph generation tools,有额外的依赖关系。尽管它们不是简单构建的强制要求,但仍然强烈推荐使用:

代码语言:javascript复制
python (version 2.7 or any later)
  • Configuration interface dependencies:

对于这些库,您需要同时安装运行时数据和开发数据,在许多发行版中,这些数据是单独打包的。开发包通常有一个-dev-devel后缀。

代码语言:javascript复制
ncurses5 to use the menuconfig interface
qt5 to use the xconfig interface
glib2, gtk2 and glade2 to use the gconfig interface
  • Source fetching tools:

在官方树中,大多数包源都是使用wgetftphttphttps位置检索的。少数软件包只能通过版本控制系统获得。此外,Buildroot还可以通过其他工具下载资源,如rsyncscp(参阅第20章,下载基础设施了解更多细节)。如果您使用以下任何一种方法启用包,您将需要在主机系统上安装相应的工具:

代码语言:javascript复制
bazaar
cvs
git
mercurial
rsync
scp
subversion
  • Java-related packages, if the Java Classpath needs to be built for the target system:
代码语言:javascript复制
The javac compiler
The jar tool
  • Documentation generation tools:
代码语言:javascript复制
asciidoc, version 8.6.3 or higher
w3m
python with the argparse module (automatically present in 2.7  and 3.2 )
dblatex (required for the pdf manual only)
  • Graph generation tools:
代码语言:javascript复制
graphviz to use graph-depends and <pkg>-graph-depends
python-matplotlib to use graph-build

3. Getting Buildroot

Buildroot版本每3个月发布一次,分别是在2月、5月、8月和11月。版本号的格式为YYYY.MM,例如2013.02,2014.08。发布tarball可以在http://buildroot.org/downloads/上找到。

有两种方式可以搭建起 Buildroot 开发环境:

  • 1、Virtualbox 虚拟机

为方便起见,在Buildroot源代码树的support/misc/Vagrantfile中提供了一个Vagrantfile,用于快速设置一个虚拟机,其中包含启动所需的依赖项。

如果你想在Linux或Mac Os X上建立一个独立的构建根环境,请将这一行粘贴到你的终端上:

代码语言:javascript复制
curl -O https://buildroot.org/downloads/Vagrantfile; vagrant up

如果你在Windows上,把这个粘贴到你的powershell:

代码语言:javascript复制
(new-object System.Net.WebClient).DownloadFile(
"https://buildroot.org/downloads/Vagrantfile","Vagrantfile");
vagrant up
  • 2、手工下载

如果您想继续开发,可以使用日常快照或复制Git存储库。更多详细信息,请参考Buildroot网站的下载页面。

4. Buildroot quick start

重要:你可以并且应该像普通用户一样构建一切。配置和使用Buildroot不需要是root。通过作为普通用户运行所有命令,可以保护系统免受包在编译和安装期间行为不正常的影响。

4.1 configuration

使用Buildroot的第一步是创建一个配置。Buildroot有一个很好的配置工具,类似于您可以在Linux内核或BusyBox中找到的那个。

From the buildroot directory, run

代码语言:javascript复制
 $ make menuconfig

for the original curses-based configurator, or

代码语言:javascript复制
 $ make nconfig

for the new curses-based configurator, or

代码语言:javascript复制
 $ make xconfig

for the Qt-based configurator, or

代码语言:javascript复制
 $ make gconfig

for the GTK-based configurator.

所有这些make命令都需要构建一个配置实用程序(包括接口),因此您可能需要为配置实用程序使用的相关库安装“开发”包。请参阅第2章 系统需求,以获得更多的细节,特别是可选的需求,以获得您喜欢的接口的依赖关系。

对于配置工具中的每个菜单项,您可以找到描述该项用途的相关帮助。关于一些具体配置方面的细节,请参阅第6章 Buildroot配置。

一旦一切配置完成,配置工具将生成一个包含整个配置的.config文件。这个文件将由顶级Makefile读取。

4.2 build

要启动构建过程,只需运行:

代码语言:javascript复制
 $ make

默认情况下,Buildroot不支持顶级并行构建,所以没有必要运行make -jN。不过,也有对顶层并行构建的实验性支持,请参见8.12节“顶层并行构建”。

上述make命令一般执行如下步骤:

  • download source files (as required);// 下载源文件(根据需要);
  • configure, build and install the cross-compilation toolchain, or simply import an external toolchain;// 配置、构建和安装交叉编译工具链,或者简单地导入外部工具链;
  • configure, build and install selected target packages;// 配置、构建和安装选定的目标包;
  • build a kernel image, if selected;// 如果选择,构建一个内核映像;
  • build a bootloader image, if selected;// 如果选择,构建一个引导加载程序映像;
  • create a root filesystem in selected formats.// 以选定的格式创建根文件系统。

Buildroot输出存储在单个目录output/中。这个目录包含几个子目录:

  • images/ where all the images (kernel image, bootloader and root filesystem images) are stored. These are the files you need to put on your target system.
  • // 存储所有映像(内核映像、引导加载程序映像和根文件系统映像)的地方。这些是您需要放到目标系统中的文件。
  • build/ where all the components are built (this includes tools needed by Buildroot on the host and packages compiled for the target). This directory contains one subdirectory for each of these components. // 所有组件都是在这里构建的(这包括Buildroot在主机上需要的工具和为目标编译的包)。这个目录包含每个组件的一个子目录。
  • host/ contains both the tools built for the host, and the sysroot of the target toolchain. The former is an installation of tools compiled for the host that are needed for the proper execution of Buildroot, including the cross-compilation toolchain. The latter is a hierarchy similar to a root filesystem hierarchy. It contains the headers and libraries of all user-space packages that provide and install libraries used by other packages. However, this directory is not intended to be the root filesystem for the target: it contains a lot of development files, unstripped binaries and libraries that make it far too big for an embedded system. These development files are used to compile libraries and applications for the target that depend on other libraries.
  • // 包含为该主机构建的工具和目标工具链的sysroot。前者是为正确执行Buildroot所需的主机编译的工具的安装,包括交叉编译工具链。后者是类似于根文件系统层次结构的层次结构。它包含所有提供和安装其他包使用的库的用户空间包的头和库。但是,这个目录并不打算作为目标的根文件系统:它包含大量开发文件、未剥离的二进制文件和库,这使得它对于嵌入式系统来说太大了。这些开发文件用于为依赖于其他库的目标编译库和应用程序。
  • staging/ is a symlink to the target toolchain sysroot inside host/, which exists for backwards compatibility.
  • // 指向host/内部目标工具链sysroot的符号链接,它的存在是为了向后兼容。
  • target/ which contains almost the complete root filesystem for the target: everything needed is present except the device files in /dev/ (Buildroot can’t create them because Buildroot doesn’t run as root and doesn’t want to run as root). Also, it doesn’t have the correct permissions (e.g. setuid for the busybox binary). Therefore, this directory should not be used on your target. Instead, you should use one of the images built in the images/ directory. If you need an extracted image of the root filesystem for booting over NFS, then use the tarball image generated in images/ and extract it as root. Compared to staging/, target/ contains only the files and libraries needed to run the selected target applications: the development files (headers, etc.) are not present, the binaries are stripped.
  • // 几乎包含了目标的完整根文件系统:所有需要的东西都存在,除了/dev/中的设备文件(Buildroot不能创建它们,因为Buildroot不是作为root运行的,也不想作为root运行)。此外,它没有正确的权限(例如busybox二进制文件的setuid)。因此,不应该在目标上使用这个目录。相反,您应该使用images/目录中构建的映像。如果您需要根文件系统的解压映像以用于在NFS上引导,那么使用images/中生成的tarball映像并将其解压为根文件。与staging/相比,target/只包含运行所选目标应用程序所需的文件和库:开发文件(头文件等)不存在,二进制文件被剥离调试信息。

这些命令make menuconfig|nconfig|gconfig|xconfigmake是最基本的命令,它们允许您通过启用的所有特性和应用程序轻松快速地生成符合您需求的图像。

关于make命令使用的更多细节在8.1节“make tips”中给出。

5. Community resources

社区资源 (略)。

II. User guide

6. Buildroot configuration

make *config中的所有配置选项都有一个帮助文本,提供关于该选项的详细信息。

make *config命令也提供了一个搜索工具。阅读不同前端菜单中的帮助信息,了解如何使用它:

  • menuconfig中,搜索工具通过按/;
  • xconfig中,通过按Ctrl f调用搜索工具。

搜索结果显示匹配项的帮助信息。在menuconfig中,左边列中的数字为相应的条目提供了快捷方式。只要输入这个数字就可以直接跳转到条目,或者跳转到包含的菜单(如果条目由于缺少依赖项而无法选择的话)。

尽管条目的菜单结构和帮助文本应该具有足够的自解释性,但有一些主题需要额外的解释,这些内容不容易在帮助文本中介绍,因此将在下面的部分中介绍。

6.1. Cross-compilation toolchain

编译工具链是一组允许您为系统编译代码的工具。它包括一个编译器(在我们的例子中是gcc)、汇编器和链接器之类的二进制utils(在我们的例子中是binutils)和一个C标准库(例如GNU Libc, uClibc-ng)。

安装在开发站上的系统肯定已经有一个编译工具链,您可以使用它编译在系统上运行的应用程序。如果您使用的是PC,那么编译工具链运行在x86处理器上,并为x86处理器生成代码。在大多数Linux系统下,编译工具链使用GNU libc (glibc)作为C标准库。这个编译工具链称为“宿主编译工具链”。运行它和您工作的机器称为“主机系统”[3]。

编译工具链由您的发行版提供,而Buildroot与它无关(除了使用它来构建交叉编译工具链和在开发主机上运行的其他工具)。

如上所述,系统附带的编译工具链运行在主机系统中的处理器上并为其生成代码。由于嵌入式系统具有不同的处理器,因此需要一个交叉编译工具链——一个运行在主机系统上但为目标系统(和目标处理器)生成代码的编译工具链。例如,如果您的主机系统使用x86,而目标系统使用ARM,那么主机上的常规编译工具链运行在x86上并生成针对x86的代码,而交叉编译工具链运行在x86上并生成针对ARM的代码。

Buildroot为交叉编译工具链提供了两种解决方案:

  • 内部工具链后端(Internal toolchain backend),在配置界面中称为Buildroot工具链(Buildroot toolchain)。
  • 外部工具链后端(External toolchain backend),在配置界面中称为外部工具链(External toolchain)。

使用Toolchain菜单中的Toolchain Type选项可以在这两个解决方案之间进行选择。一旦选择了一个解决方案,就会出现许多配置选项,以下部分将详细介绍这些选项。

6.1.1. Internal toolchain backend

在为目标嵌入式系统构建用户空间应用程序和库之前,内部工具链后端是Buildroot自己构建交叉编译工具链的后端。

这个后端支持几个C库:uClibc-ngglibcmusl

一旦您选择了这个后端,就会出现许多选项。最重要的是以下选项:

  • Change the version of the Linux kernel headers used to build the toolchain. This item deserves a few explanations. In the process of building a cross-compilation toolchain, the C library is being built. This library provides the interface between userspace applications and the Linux kernel. In order to know how to “talk” to the Linux kernel, the C library needs to have access to the Linux kernel headers (i.e. the .h files from the kernel), which define the interface between userspace and the kernel (system calls, data structures, etc.). Since this interface is backward compatible, the version of the Linux kernel headers used to build your toolchain do not need to match exactly the version of the Linux kernel you intend to run on your embedded system. They only need to have a version equal or older to the version of the Linux kernel you intend to run. If you use kernel headers that are more recent than the Linux kernel you run on your embedded system, then the C library might be using interfaces that are not provided by your Linux kernel.
  • // 更改用于构建工具链的Linux内核头文件的版本。这一项值得作一些解释。在构建交叉编译工具链的过程中,正在构建C库。这个库提供了用户空间应用程序和Linux内核之间的接口。为了知道如何与Linux内核“对话”,C库需要访问Linux内核的头文件(即来自内核的.h文件),它定义了用户空间和内核之间的接口(系统调用、数据结构等)。因为这个接口是向后兼容的,所以用于构建工具链的Linux内核头的版本不需要与您打算在嵌入式系统上运行的Linux内核的版本完全匹配。它们只需要一个与您要运行的Linux内核版本相同或更老的版本即可。如果您使用的内核头比您在嵌入式系统上运行的Linux内核更新,那么C库可能使用的接口不是由您的Linux内核提供的。
  • Change the version of the GCC compiler, binutils and the C library.
  • // 更改GCC编译器、binutils和C库的版本。
  • Select a number of toolchain options (uClibc only): whether the toolchain should have RPC support (used mainly for NFS), wide-char support, locale support (for internationalization), C support or thread support. Depending on which options you choose, the number of userspace applications and libraries visible in Buildroot menus will change: many applications and libraries require certain toolchain options to be enabled. Most packages show a comment when a certain toolchain option is required to be able to enable those packages. If needed, you can further refine the uClibc configuration by running make uclibc-menuconfig. Note however that all packages in Buildroot are tested against the default uClibc configuration bundled in Buildroot: if you deviate from this configuration by removing features from uClibc, some packages may no longer build.
  • // 选择一些工具链选项(仅限uClibc):工具链是否应该有RPC支持(主要用于NFS)、宽字符支持、区域支持(用于国际化)、c 支持或线程支持。根据您选择的选项,可见于Buildroot菜单中的用户空间应用程序和库的数量将会改变:许多应用程序和库需要启用某些工具链选项。当需要某个工具链选项来启用这些包时,大多数包都会显示注释。如果需要,您可以通过运行make uClibc -menuconfig来进一步优化uClibc配置。但是请注意,Buildroot中的所有包都是根据默认的uClibc配置进行测试的:如果你通过从uClibc中删除特性而偏离这个配置,一些包可能不再构建。

值得注意的是,每当其中一个选项被修改时,就必须重新构建整个工具链和系统。请参阅第8.2节 “了解什么时候需要进行完全重建”。

这个后端的优点:

  • Well integrated with Buildroot // 与Buildroot集成良好
  • Fast, only builds what’s necessary // 快速,只构建必要的内容

这个后端的缺点:

  • Rebuilding the toolchain is needed when doing make clean, which takes time. If you’re trying to reduce your build time, consider using the External toolchain backend.
  • // 在做make clean时需要重建工具链,这需要时间。如果您试图减少构建时间,请考虑使用External工具链后端。
6.1.2. External toolchain backend

外部工具链后端允许使用现有的预构建的交叉编译工具链。Buildroot知道许多著名的交叉编译工具链(从Linaro for ARM、Sourcery CodeBench for ARM、x86-64、PowerPC和MIPS),并且能够自动下载它们,或者它可以指向一个定制的工具链,可以下载或在本地安装。

目前,你有三个解决方案来使用外部工具链:

  • Use a predefined external toolchain profile, and let Buildroot download, extract and install the toolchain. Buildroot already knows about a few CodeSourcery and Linaro toolchains. Just select the toolchain profile in Toolchain from the available ones. This is definitely the easiest solution.
  • // 使用预定义的外部工具链概要文件,并让Buildroot下载、提取和安装工具链。Buildroot已经知道一些CodeSourcery和Linaro工具链。只需在Toolchain中从可用的工具链概要文件中选择工具链概要文件。这绝对是最简单的解决方案。
  • Use a predefined external toolchain profile, but instead of having Buildroot download and extract the toolchain, you can tell Buildroot where your toolchain is already installed on your system. Just select the toolchain profile in Toolchain through the available ones, unselect Download toolchain automatically, and fill the Toolchain path text entry with the path to your cross-compiling toolchain.
  • // 使用一个预定义的外部工具链概要文件,但是不必让Buildroot下载和提取工具链,您可以告诉Buildroot您的工具链已经安装在系统的哪个位置。只需在Toolchain中选择工具链配置文件,取消选择自动下载工具链,并在Toolchain path文本条目中填写交叉编译工具链的路径。
  • Use a completely custom external toolchain. This is particularly useful for toolchains generated using crosstool-NG or with Buildroot itself. To do this, select the Custom toolchain solution in the Toolchain list. You need to fill the Toolchain path, Toolchain prefix and External toolchain C library options. Then, you have to tell Buildroot what your external toolchain supports. If your external toolchain uses the glibc library, you only have to tell whether your toolchain supports C or not and whether it has built-in RPC support. If your external toolchain uses the uClibc library, then you have to tell Buildroot if it supports RPC, wide-char, locale, program invocation, threads and C . At the beginning of the execution, Buildroot will tell you if the selected options do not match the toolchain configuration.
  • // 使用完全自定义的外部工具链。这对于使用crosstool-NGBuildroot本身生成的工具链特别有用。为此,在Toolchain列表中选择Custom toolchain解决方案。您需要填充Toolchain pathToolchain prefixExternal toolchain C library选项。然后,你必须告诉Buildroot你的外部工具链支持什么。如果您的外部工具链使用glibc库,您只需告诉您的工具链是否支持c ,以及它是否有内置的RPC支持。如果您的外部工具链使用了uClibc库,那么您必须告诉Buildroot它是否支持RPC、宽字符、区域设置、程序调用、线程和c 。在执行的开始,Buildroot将告诉您所选择的选项是否与工具链配置不匹配。

我们的外部工具链支持已经通过来自CodeSourceryLinaro的工具链、由crosstool-NG生成的工具链和由Buildroot本身生成的工具链进行了测试。一般来说,所有支持sysroot特性的工具链都应该工作。如果没有,不要犹豫联系开发人员。

我们不支持openenembeddedYocto生成的工具链或SDK,因为这些工具链不是纯工具链(即编译器、binutils、C和c 库)。相反,这些工具链带有一组非常大的预编译库和程序。因此,Buildroot不能导入工具链的sysroot,因为它将包含数百兆字节的预编译库,而这些库通常是由Buildroot构建的。

我们也不支持使用发行版工具链(即由发行版安装的gcc/binutils/C库)作为构建目标软件的工具链。这是因为你的分发工具链不是一个“纯”的工具链(即只使用C/ c 库),所以我们不能正确地将它导入Buildroot构建环境中。因此,即使您正在为x86或x86_64目标构建系统,也必须使用Buildroot或crosstool-NG生成交叉编译工具链。

如果你想为你的项目生成一个自定义的工具链,可以在Buildroot中作为外部工具链使用,我们的建议是使用Buildroot本身(见6.1.3节“使用Buildroot构建一个外部工具链”)或者使用crosstool-NG。

这个后端的优点:

  • Allows to use well-known and well-tested cross-compilation toolchains. // 允许使用众所周知和经过良好测试的交叉编译工具链。
  • Avoids the build time of the cross-compilation toolchain, which is often very significant in the overall build time of an embedded Linux system. // 避免交叉编译工具链的构建时间,这在嵌入式Linux系统的总体构建时间中通常非常重要。

这个后端的缺点:

  • If your pre-built external toolchain has a bug, may be hard to get a fix from the toolchain vendor, unless you build your external toolchain by yourself using Buildroot or Crosstool-NG.
  • // 如果你预构建的外部工具链有bug,可能很难从工具链供应商那里得到修复,除非你自己使用Buildroot或Crosstool-NG构建自己的外部工具链。
6.1.3. Build an external toolchain with Buildroot

Buildroot内部工具链选项可用于创建外部工具链。下面是构建内部工具链并将其打包以供Buildroot自身(或其他项目)重用的一系列步骤。

1、创建一个新的Buildroot配置,详细信息如下:

  • Select the appropriate Target options for your target CPU architecture
  • In the Toolchain menu, keep the default of Buildroot toolchain for Toolchain type, and configure your toolchain as desired
  • In the System configuration menu, select None as the Init system and none as /bin/sh
  • In the Target packages menu, disable BusyBox
  • In the Filesystem images menu, disable tar the root filesystem

2、然后,我们可以触发构建,并要求Buildroot生成一个SDK。这将方便地为我们生成一个包含工具链的tarball:

代码语言:javascript复制
make sdk

这将在$(O)/images中生成SDK tarball,其名称类似于arm-buildroot-linux-uclibcgnueabi_sdk-buildroot.tar.gz。保存这个tarball,因为现在它是您可以在其他Buildroot项目中作为外部工具链重用的工具链。

3、在其他的Buildroot项目中,在Toolchain菜单中:

  • Set Toolchain type to External toolchain
  • Set Toolchain to Custom toolchain
  • Set Toolchain origin to Toolchain to be downloaded and installed
  • Set Toolchain URL to file:///path/to/your/sdk/tarball.tar.gz
6.1.4. External toolchain wrapper

当使用外部工具链时,Buildroot生成一个wrapper程序,该程序透明地将适当的选项(根据配置)传递给外部工具链程序。如果您需要调试这个wrapper来检查传递了哪些参数,您可以将环境变量BR2_DEBUG_WRAPPER设置为以下任意一个:

  • 0, empty or not set: no debug
  • 1: trace all arguments on a single line
  • 2: trace one argument per line

6.2. /dev management

在Linux系统中,/dev目录包含特殊的文件,称为设备文件(device files),允许用户空间应用程序访问Linux内核管理的硬件设备。如果没有这些设备文件,您的用户空间应用程序将不能使用硬件设备,即使它们被Linux内核正确识别。

System configuration,/dev management下,Buildroot提供了四种不同的解决方案来处理/dev目录:

  • The first solution is Static using device table. This is the old classical way of handling device files in Linux. With this method, the device files are persistently stored in the root filesystem (i.e. they persist across reboots), and there is nothing that will automatically create and remove those device files when hardware devices are added or removed from the system. Buildroot therefore creates a standard set of device files using a device table, the default one being stored in system/device_table_dev.txt in the Buildroot source code. This file is processed when Buildroot generates the final root filesystem image, and the device files are therefore not visible in the output/target directory. The BR2_ROOTFS_STATIC_DEVICE_TABLE option allows to change the default device table used by Buildroot, or to add an additional device table, so that additional device files are created by Buildroot during the build. So, if you use this method, and a device file is missing in your system, you can for example create a board/<yourcompany>/<yourproject>/device_table_dev.txt file that contains the description of your additional device files, and then you can set BR2_ROOTFS_STATIC_DEVICE_TABLE to system/device_table_dev.txt board/<yourcompany>/<yourproject>/device_table_dev.txt. For more details about the format of the device table file, see Chapter 25, Makedev syntax documentation.
  • // 第一个解决方案是静态使用设备表。这是Linux中处理设备文件的古老的经典方法。使用此方法,设备文件将持久化地存储在根文件系统中(即,它们在重新引导时持久化),当从系统中添加或删除硬件设备时,不会自动创建和删除这些设备文件。因此,Buildroot使用设备表创建一组标准的设备文件,默认的设备表存储在Buildroot源代码中的system/device_table_dev.txt中。这个文件在Buildroot生成最终的根文件系统映像时被处理,因此设备文件在输出/目标目录中是不可见的。BR2_ROOTFS_STATIC_DEVICE_TABLE选项允许更改Buildroot使用的默认设备表,或添加一个额外的设备表,以便Buildroot在构建期间创建额外的设备文件。所以,如果你使用这个方法,并且你的系统中缺少一个设备文件,例如,你可以创建一个board///device_table_dev.txt文件,其中包含你的附加设备文件的描述,然后你可以设置BR2_ROOTFS_STATIC_DEVICE_TABLEsystem/device_table_dev.txt board/<yourcompany>/<yourproject>/device_table_dev.txt。有关设备表文件格式的更多详细信息,请参见第25章Makedev语法文档。
  • The second solution is Dynamic using devtmpfs only. devtmpfs is a virtual filesystem inside the Linux kernel that has been introduced in kernel 2.6.32 (if you use an older kernel, it is not possible to use this option). When mounted in /dev, this virtual filesystem will automatically make device files appear and disappear as hardware devices are added and removed from the system. This filesystem is not persistent across reboots: it is filled dynamically by the kernel. Using devtmpfs requires the following kernel configuration options to be enabled: CONFIG_DEVTMPFS and CONFIG_DEVTMPFS_MOUNT. When Buildroot is in charge of building the Linux kernel for your embedded device, it makes sure that those two options are enabled. However, if you build your Linux kernel outside of Buildroot, then it is your responsibility to enable those two options (if you fail to do so, your Buildroot system will not boot).
  • // 第二个解决方案是仅使用devtmpfs动态。devtmpfs是内核2.6.32中引入的Linux内核中的一个虚拟文件系统(如果使用旧内核,则不可能使用此选项)。当挂载到/dev中时,这个虚拟文件系统将自动使设备文件随着硬件设备的添加和从系统中移除而出现和消失。这个文件系统在重新引导时不是持久的:它是由内核动态填充的。使用devtmpfs需要启用以下内核配置选项:CONFIG_DEVTMPFSCONFIG_DEVTMPFS_MOUNT。当Buildroot负责为您的嵌入式设备构建Linux内核时,它会确保启用这两个选项。但是,如果您在Buildroot之外构建Linux内核,那么您就有责任启用这两个选项(如果您没有这样做,那么您的Buildroot系统将无法引导)。
  • The third solution is Dynamic using devtmpfs mdev. This method also relies on the devtmpfs virtual filesystem detailed above (so the requirement to have CONFIG_DEVTMPFS and CONFIG_DEVTMPFS_MOUNT enabled in the kernel configuration still apply), but adds the mdev userspace utility on top of it. mdev is a program part of BusyBox that the kernel will call every time a device is added or removed. Thanks to the /etc/mdev.conf configuration file, mdev can be configured to for example, set specific permissions or ownership on a device file, call a script or application whenever a device appears or disappear, etc. Basically, it allows userspace to react on device addition and removal events. mdev can for example be used to automatically load kernel modules when devices appear on the system. mdev is also important if you have devices that require a firmware, as it will be responsible for pushing the firmware contents to the kernel. mdev is a lightweight implementation (with fewer features) of udev. For more details about mdev and the syntax of its configuration file, see http://git.busybox.net/busybox/tree/docs/mdev.txt.
  • // 第三种解决方案是动态使用devtmpfs mdev。这个方法还依赖于上面详细介绍的devtmpfs虚拟文件系统(因此在内核配置中启用CONFIG_DEVTMPFS和CONFIG_DEVTMPFS_MOUNT的要求仍然适用),但是在它上面添加了mdev用户空间实用程序。mdev是BusyBox的一个程序部分,每次添加或删除设备时内核都会调用它。由于/etc/mdev.conf配置文件,mdev可以配置为例如,设置特定的权限或对设备文件的所有权,每当设备出现或消失时调用脚本或应用程序,等等。基本上,它允许用户空间对设备添加和删除事件做出反应。例如,当设备出现在系统上时,可以使用Mdev自动加载内核模块。如果您有需要固件的设备,Mdev也很重要,因为它将负责将固件内容推送到内核。Mdev是udev的一个轻量级实现(具有更少的特性)。有关mdev及其配置文件语法的详细信息,请参见http://git.busybox.net/busybox/tree/docs/mdev.txt。
  • The fourth solution is Dynamic using devtmpfs eudev. This method also relies on the devtmpfs virtual filesystem detailed above, but adds the eudev userspace daemon on top of it. eudev is a daemon that runs in the background, and gets called by the kernel when a device gets added or removed from the system. It is a more heavyweight solution than mdev, but provides higher flexibility. eudev is a standalone version of udev, the original userspace daemon used in most desktop Linux distributions, which is now part of Systemd. For more details, see http://en.wikipedia.org/wiki/Udev.
  • // 第四种解决方案是动态使用devtmpfs eudev。这个方法也依赖于上面详细介绍的devtmpfs虚拟文件系统,但是在它上面添加了eudev用户空间守护进程。Eudev是一个在后台运行的守护进程,当设备从系统中添加或删除时,内核会调用它。它是一个比mdev更重量级的解决方案,但提供了更高的灵活性。eudev是udev的一个独立版本,udev是大多数桌面Linux发行版中使用的原始用户空间守护进程,现在是Systemd的一部分。更多信息请参见http://en.wikipedia.org/wiki/Udev。

Buildroot开发人员的建议是从Dynamic using devtmpfs only的解决方案开始,直到您需要通知用户空间何时添加/删除设备,或是否需要固件,在这种情况下,Dynamic using devtmpfs mdev通常是一个很好的解决方案。

注意,如果选择systemd作为init系统,/dev管理将由systemd提供的udev程序执行。

6.3. init system

init程序是由内核启动的第一个用户空间程序(它的PID号为1),负责启动用户空间服务和程序(例如:web服务器、图形应用程序、其他网络服务器等)。

Buildroot允许使用三种不同类型的初始化系统,可以从System configuration, Init system中选择:

  • The first solution is BusyBox. Amongst many programs, BusyBox has an implementation of a basic init program, which is sufficient for most embedded systems. Enabling the BR2_INIT_BUSYBOX will ensure BusyBox will build and install its init program. This is the default solution in Buildroot. The BusyBox init program will read the /etc/inittab file at boot to know what to do. The syntax of this file can be found in http://git.busybox.net/busybox/tree/examples/inittab (note that BusyBox inittab syntax is special: do not use a random inittab documentation from the Internet to learn about BusyBox inittab). The default inittab in Buildroot is stored in system/skeleton/etc/inittab. Apart from mounting a few important filesystems, the main job the default inittab does is to start the /etc/init.d/rcS shell script, and start a getty program (which provides a login prompt).
  • // 第一个解决方案是BusyBox。在许多程序中,BusyBox有一个基本的init程序的实现,这对于大多数嵌入式系统来说已经足够了。启用BR2_INIT_BUSYBOX将确保BusyBox将构建并安装它的init程序。这是Buildroot中的默认解决方案。BusyBox初始化程序将在启动时读取/etc/inittab文件,以知道要做什么。该文件的语法可以在http://git.busybox.net/busybox/tree/examples/inittab中找到(注意,BusyBox的inittab语法是特殊的:不要使用Internet上随机的inittab文档来了解BusyBox的inittab)。“Buildroot”默认的“inittab”存放在“system/skeleton/etc/inittab”中。除了挂载一些重要的文件系统外,默认的inittab所做的主要工作是启动/etc/init. confd/rcS shell脚本,并启动getty程序(提供登录提示)。
  • The second solution is systemV. This solution uses the old traditional sysvinit program, packed in Buildroot in package/sysvinit. This was the solution used in most desktop Linux distributions, until they switched to more recent alternatives such as Upstart or Systemd. sysvinit also works with an inittab file (which has a slightly different syntax than the one from BusyBox). The default inittab installed with this init solution is located in package/sysvinit/inittab.
  • // 第二个解决方案是systemV。这个解决方案使用旧的传统的sysvinit程序,打包在Buildroot中的package/sysvinit。这是在大多数桌面Linux发行版中使用的解决方案,直到他们转向更近期的替代方案,如Upstart或Systemd。sysvinit还可以使用inittab文件(与BusyBox中的文件语法略有不同)。与此init解决方案一起安装的默认inittab位于package/sysvinit/inittab中。
  • The third solution is systemd. systemd is the new generation init system for Linux. It does far more than traditional init programs: aggressive parallelization capabilities, uses socket and D-Bus activation for starting services, offers on-demand starting of daemons, keeps track of processes using Linux control groups, supports snapshotting and restoring of the system state, etc. systemd will be useful on relatively complex embedded systems, for example the ones requiring D-Bus and services communicating between each other. It is worth noting that systemd brings a fairly big number of large dependencies: dbus, udev and more. For more details about systemd, see http://www.freedesktop.org/wiki/Software/systemd.
  • // 第三个解决方案是系统化的。systemd是Linux系统的新一代init系统。它比传统的初始化程序做得更多:使用socket和D-Bus激活来启动服务,提供按需启动守护进程,使用Linux控制组跟踪进程,支持系统状态的快照和恢复等。systemd在相对复杂的嵌入式系统上非常有用。例如需要D-Bus和服务相互通信的。值得注意的是,systemd带来了相当多的大型依赖:dbus, udev等等。有关systemd的更多信息,请参见http://www.freedesktop.org/wiki/Software/systemd。

Buildroot开发人员推荐的解决方案是使用BusyBox init,因为它对于大多数嵌入式系统来说已经足够了。Systemd可以用于更复杂的情况。

7. Configuration of other components

在尝试修改下面的任何组件之前,请确保您已经配置了Buildroot本身,并启用了相应的包。

  • BusyBox

如果您已经有一个BusyBox配置文件,您可以直接在Buildroot配置中指定这个文件,使用BR2_PACKAGE_BUSYBOX_CONFIG。否则,Buildroot将从默认的BusyBox配置文件启动。

要对配置进行后续更改,请使用make busybox-menuconfig打开BusyBox配置编辑器。

还可以通过环境变量指定BusyBox配置文件,不过不建议这样做。请参阅8.6节“环境变量”了解更多细节。

  • uClibc

uClibc的配置方法与BusyBox相同。指定现有配置文件的配置变量是BR2_UCLIBC_CONFIG。进行后续更改的命令是make uclibc-menuconfig

  • Linux kernel

如果您已经有了一个内核配置文件,那么可以使用BR2_LINUX_KERNEL_USE_CUSTOM_CONFIG在Buildroot配置中直接指定这个文件。

如果您还没有内核配置文件,那么您可以使用BR2_LINUX_KERNEL_USE_DEFCONFIG在Buildroot配置中指定defconfig,或者使用BR2_LINUX_KERNEL_USE_CUSTOM_CONFIG创建一个空文件并将其指定为自定义配置文件。

要对配置进行后续更改,请使用make Linux-menuconfig打开Linux配置编辑器。

  • Barebox

Barebox的配置方法与Linux内核的配置方法相同。对应的配置变量是BR2_TARGET_BAREBOX_USE_CUSTOM_CONFIGBR2_TARGET_BAREBOX_USE_DEFCONFIG。要打开配置编辑器,请使用make barebox-menuconfig

  • U-Boot

U-Boot(2015.04及以上版本)的配置方法与Linux内核相同。对应的配置变量是BR2_TARGET_UBOOT_USE_CUSTOM_CONFIGBR2_TARGET_UBOOT_USE_DEFCONFIG。打开配置编辑器,使用make uboot-menuconfig

8. General Buildroot usage

8.1. make tips

这是一组技巧,可以帮助你充分利用Buildroot。

  • Display all commands executed by make:
代码语言:javascript复制
 $ make V=1 <target>
  • Display the list of boards with a defconfig:
代码语言:javascript复制
 $ make list-defconfigs
  • Display all available targets:
代码语言:javascript复制
 $ make help

并不是所有的目标都是可用的,.config文件中的一些设置可能会隐藏一些目标:

busybox-menuconfig only works when busybox is enabled; linux-menuconfig and linux-savedefconfig only work when linux is enabled; uclibc-menuconfig is only available when the uClibc C library is selected in the internal toolchain backend; barebox-menuconfig and barebox-savedefconfig only work when the barebox bootloader is enabled. uboot-menuconfig and uboot-savedefconfig only work when the U-Boot bootloader is enabled.

  • Cleaning`: Explicit cleaning is required when any of the architecture or toolchain configuration options are changed. // 当任何架构或工具链配置选项发生更改时,需要显式清理。

To delete all build products (including build directories, host, staging and target trees, the images and the toolchain)

0 人点赞