• 二、buildroot 构建交叉编译工具链【转】


    转自:https://www.cnblogs.com/kele-dad/p/13125808.html

    2.1 介绍

    2.1.1 工具链简介

    一个编译工具链模块是允许为系统编译代码的一组工具。它由一个编译器(在我们的例子中是 gcc)、像汇编器和链接器这样的二进制 utils(一般是 binutils)和一个C标准库(例如 GNU Libc, uClibc-ng)组成。

    一个交叉编译工具链是可有在主机上运行的,但是编译出来的二进制文件只能运行在目标板或机器上。在我们的宿主机上也有工具链,它只能编译适用于我们的宿主机,编译出来的程序也只能运行在我们的宿主机上。

    当前我们要使用 buildroot 编译出来一个交叉编译工具链,适用于我们的目标板。

    目标板是 S3C2440,它是 ARM 架构的,arm920t 的核心。

    2.1.2 buildroot 的工具链工具

    buildroot 提供了两种建立交叉编译工具链的方式:

    • 内部工具链后端,在配置接口中称为 Buildroot 工具链。
    • 外部工具链后端,在配置接口中称为外部工具链。

    使用工具链菜单中的工具链类型选项来选择这两种解决方案。一旦选择了一个解决方案,就会出现许多配置选项。

    在 根目录下使用 make menuconfig,Toolchain--->Toolchain type

    2.1.3 内部工具链

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

    此交叉编译工具链支持几种 C 库:uClibc-ngglibc 和 musl。

    一旦选择这个类型的工具链后,大量的选项将出现。最重要的选项如下:

    • 更改构建工具链需要的内核头文件版本。
      • 在构建交叉编译工具链的过程中,C 库也在被构建。这个库提供了用户空间应用程序和 Linux 内核之间的接口。为了知道如何与 Linux 内核“对话”,C 库需要访问Linux内核头文件(即来自内核的.h文件),它定义了用户空间与内核之间的接口(系统调用、数据结构等)。
      • 由于此接口是向后兼容的,因此用于构建工具链的 Linux 内核头的版本不需要与我们打算在嵌入式系统上运行的 Linux 内核的版本完全匹配。它们只需要有一个与我们要运行的 Linux 内核版本相同或更老的版本。
      • 如果我们使用的内核头文件比我们在嵌入式系统上运行的 Linux 内核更新,那么C 库可能使用的接口不是我们的 Linux 内核提供的。
    • 更改 GCC 编译器、binutils 和 C 库的版本
    • 选择编译器选项(只有使用 uClibc 的时候需要)
      • 工具链是否应该有 RPC 支持(主要用于 NFS)、宽字符支持、语言环境支持(用于国际化)、c++ 支持或线程支持。
      • 根据我们选择的选项,Buildroot 菜单中可见的用户空间应用程序和库的数量将会改变:许多应用程序和库需要启用某些工具链选项。
      • 当需要某个工具链选项来启用那些包时,大多数包都会显示注释。如果需要,可以通过运行 make uClibc -menuconfig 进一步优化 uClibc 配置。
      • 但是请注意,Buildroot中 的所有包都是根据内置的默认 uClibc 配置进行测试的:如果通过删除 uClibc 的特性而偏离了这个配置,那么一些包可能不再构建。 

    值得注意的是,每当修改其中一个选项时,就必须重新构建整个工具链和系统。

    这种方式也有好处:与 Buildroot 有很好的集成并且快速,只构建必要的内容

    缺点是:make clean 后需要重新构建工具链,这需要时间。如果我们试图减少构建时间,可以考虑使用外部工具链。

    2.1.4 外部工具链

     外部工具链允许使用现有的预先构建的交叉编译工具链。

    Buildroot知道许多著名的交叉编译工具链(来自用于 ARM 的 Linaro、用于 ARM 的 Sourcery CodeBench、x86-64、PowerPC 和 MIPS),并且能够自动下载它们,或者指向一个定制的工具链,可以下载,也可以在本地安装。

    我们有三种方式使用一个外部工具链:

    • 使用预定义的外部工具链配置文件,并让 Buildroot 下载、提取和安装工具链。Buildroot 已经知道一些 CodeSourcery 和 Linaro 工具链。从可用的工具链中选择工具链配置文件。这绝对是最简单的解决方案。
    • 使用预定义的外部工具链配置文件,但不是让 Buildroot 下载和提取工具链,我们可以告诉 Buildroot 我们的工具链已经安装在系统的哪个位置。只需通过可用的工具链选择工具链配置文件,自动取消选择下载工具链,并用交叉编译工具链的路径填充工具链路径
    • 使用一个完全的自定义的外部交叉编译工具链。
      • 这对于使用crosstool-NG或使用Buildroot本身生成的工具链特别有用。
      • 要做到这些,首先要在 Toolchain 配置选项中选择 Custom toolchain
      • 我们需要填写 Toolchain pathToolchain prefix 和 External toolchain C library 选项
      • 接着需要必须告诉 Buildroot 我们的外部工具链支持什么。如果外部工具链使用 glibc 库,只需要知道工具链是否支持 c++ 以及它是否有内置的 RPC 支持。如果外部工具链使用 uClibc 库,那么您必须告诉 Buildroot 它是否支持 RPC、宽字符、语言环境、程序调用、线程和c++。
      • 在执行的开始,Buildroot 会告诉我们所选选项是否与工具链配置匹配。

    如果想为自己的项目生成一个定制的工具链,它可以在 Buildroot中 使用外部工具链,建议使用 Buildroot 或 crosstool-NG 来构建它。

    • 这种构建工具链的方式的好处是:
      • 允许使用众所周知且经过良好测试的交叉编译工具链。
      • 避免交叉编译工具链的构建时间,这在嵌入式Linux系统的总体构建时间中通常非常重要。
    • 坏处是:
      • 如果预先构建的外部工具链有错误,可能很难从工具链供应商那里得到修复,除非使用Buildroot或Crosstool-NG自己构建外部工具链。

    2.2 构建工具链

    2.2.1 使用 buildrtoo 构建外部工具链

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

    make menuconfig 进入配置菜单

    Target options 选择 CPU 架构:

     ToolChain 中选择配置交叉编译工具链的一系列选项:

    • Toolchain type:选择 Buildroot toolchain
    • custom toolchain vendor name:buildroot 构建的交叉编译工具链的名字是 <arch>-<vendor>-<os>-<libc>,这个选项对应 vendor 名字,配置成 s3c24x0,那么我们生成的工具链是 arm-s3c24x0-linux-glibc
    • C library:选择 glibc
    • Kernel Headers:内核头文件,选择手动指定,或者选择里面提供的内核版本,我这里选择手动指定 Manually specified Linux version
    • linux version:Linux 版本,填入 4.4.174
    • Custom kernel headers series:自定义内核头文件系列,选择 4.4.x
    • Install glibc utilities:启用这个选项将为目标编译和安装 getconf、ldconfig、ldd 和 locale glibc实用程序。按需要选择
    • Binutils Version:binutils 版本,保持默认
    • Additional binutils options:额外的 binutils 选项,保持为空
    • GCC compiler Version:GCC 编译器版本,选择为 gcc 8.x
    • Additional gcc options:额外的 GCC 选项,保持默认为空就好,如果需要,就自己填写
    • 语言支持:可以支持 C++ ,Fortran,支持 C++即可
    • Enable compiler link-time-optimization support:此选项支持gcc中的链接时间优化(LTO)。
    • Enable compiler OpenMP support:为编译器启用 OpenMP 支持。主要是在编译时采用并行处理
    • Enable graphite support:此选项启用编译器中的石墨优化。这个选项看不懂
    • Build cross gdb for the host:构建一个运行在主机上的交叉 gdb,并调试运行在目标机上的程序。它需要在目标上安装'gdbserver',即 BR2_PACKAGE_GDB_SERVER(Target packages-> Debugging, profiling and benchmark-> gdb )
      • TUI support:此选项为gdb启用终端用户界面(TUI)
      • Python support:此选项支持交叉 gdb 中的 Python 支持。
      • Simulator support:此选项启用了交叉 gdb 中的模拟器支持。
      • GDB debugger Version:版本选择 gdb 8.2.x
    • Copy gconv libraries:gconv 库用于在不同字符集之间进行转换。如果需要存储和/或显示不同的字符集,请使用'y'。
      • Gconv libraries to copy:设置为要复制的gconv库列表。为空以复制所有gconv库。只指定库的基本名称,忽略。so扩展。如:IBM850 ISO8859-15 UNICODE。注意,gconv 库占用 8 M(在 ARM 上)。
    • Extra toolchain libraries to be copied to target:如果工具链提供了需要复制到目标文件系统的额外库,请在这里输入它们,以空格作为分割符分割。如 "libasan liblsan libtsan libubsan"
    • Enable MMU support: MMU 支持
    • Target Optimizations:为目标主机构建时使用的优化。注意:gcc优化级别是在构建选项中定义的。一般不会选择
    • Target linker options:为目标构建时要传递给链接器的额外选项。
    • Register toolchain within Eclipse Buildroot plug-in:这个选项告诉 Buildroot 生成必要的配置文件,通过 Eclipse Buildroot 插件使工具链出现在 Eclipse 中。

    System configuration 中需要禁用掉系统初始化选项和 /bin/sh:

    • Init system:选择 none
    • /bin/sh :设置为 none

    Target packages 中要禁用 busybox:

    • busybox:选项设为空

    Build options 中,需要设置一下源的路径,在执行构建的过程中,需要从不同的源地址下载各种不同的包,由于国内的和谐,所以需要更改为国内镜像:

    • Mirrors and Download locations
      • Kernel.org mirror:https://mirrors.tuna.tsinghua.edu.cn/kernel
      • GNU Software mirror:https://mirrors.tuna.tsinghua.edu.cn/gnu

    Filesystem images 中禁用 tar the root filesystem

    配置完成后,保存退出,然后执行命令 make sdk,编译完成后,如下:

     SDK 的压缩包存放再 $(O)/images 下,如果指定了 $(O),就是指定的目录,未指定则是根目录下output 目录。压缩包名为 arm-s3c24x0-linux-gnueabi_sdk-buildroot.tar.gz:

     保存这个 tarball,因为它现在是一个工具链,我们可以在其他 Buildroot 项目中重用它作为外部工具链。

    在 buildroot 下建立自己的工作源码目录 source,虽然可以按 buildroot 的架构去添加包之类的,但是太过麻烦,每次只有在编译后,才能去看源码,在开发中,更多的是便开发边修改边编译。

    复制代码
    mkdir source
    cd source
    cp ../output/images/arm-s3c24x0-linux-gnueabi_sdk-buildroot.tar.gz ./
    mkdir toolchain
    mv arm-s3c24x0-linux-gnueabi_sdk-buildroot.tar.gz ./toolchain
    cd toolchain
    tar -zxvf arm-s3c24x0-linux-gnueabi_sdk-buildroot.tar.gz
    rm -rf arm-s3c24x0-linux-gnueabi_sdk-buildroot.tar.gz
    复制代码

    现在要单独保存一下 toolchain 的配置文件:

    • 若是之前未使用 xxx_defconfig 生成的 .config 配置文件,根目录下执行 make savedefconfig 会在当前根目录下生成一个 defconfig 文件
    • 若是使用的 xxx_defconfig 生成的 .config,则执行 make update-defconfig 会自动更新 xxx_defconfig 文件
    • 生成 defconfig 后,保存到根目录下的 configs 文件夹下, cp defconfig configs/s3c24x0ToolSDK_defconfig,在自己的 source 中也保存一份 cp defconfig source/s3c24x0ToolSDK_defconfig

    保存后,执行一下 make clean,同时修改一下根目录下的 Makefile,在执行 make distclean 的时候,不要删除 dl 目录,当然如果每次都想重新下载源码包的另说,不用改。

     1070 行中,带 dl 的删除掉即可。

    同时若是使用的 git 托管代码,需要修改 .gitignore,将 dl 那一行删除即可。

    修改完成后,执行一下 make distclean,后面需要针对自己的工程进行配置,我们可以直接使用我们编译出来的工具链,作为外部工具链使用。

    make menuconfig 进入配置。

    • Target options 中的配置与交叉编译工具链的配置相同
    • Toolchain 中,
      • 将 Toolchain type 改为 External toolchain,
      • Toolchain 选择成 Custom toolchain
      • Toolchain origin 改为 Pre-installed toolchain
      • Toolchain path 填写为我们的路径:$(TOPDIR)/source/ arm-s3c24x0-linux-gnueabi_sdk-buildroot.tar.gz
      • External toolchain gcc version:改为我们编译的版本 8.x
      • External toolchain kernel headers series:头文件改为 4.4.x
      • External toolchain C library:改为 glibc
      •  Toolchain has SSP support?:勾选上
        • Toolchain has SSP strong support?:选上
      • Toolchain has RPC support?:勾选上
      • Toolchain has C++ support:勾选上
      • 其他的选项都保持和编译工具链的时候一致。

    使用外部工具链比较坑的是,执行 make 的时候,工具链又被编译了一遍。这个问题再看看

    指定 make savedefconfig 保存配置:

      mv defconfig configs/s3c24x0_defconfig

    执行 make distclean,上传至 gitee 或是 github。

    gitee 工程地址:https://gitee.com/cocosleep/project

  • 相关阅读:
    为了抓包某APP所做的尝试(to be continued)
    VirtualBox的使用的一些Tips 网络配置|硬盘扩充
    斜线和反斜线简要历史,为什么windows和unix采用不同的路径分隔符
    求出二维数组主对角线、次对角线以及周边元素之和
    C#计算两个时间的时间差,精确到年月日时分秒
    C#获取MP3,WMA信息
    C#窗体随意移动
    DEV GridControl小结
    DEV 皮肤的使用
    C#窗体阴影
  • 原文地址:https://www.cnblogs.com/sky-heaven/p/13513198.html
Copyright © 2020-2023  润新知