2017年6月

嵌入式、物联网技术交流分享

交叉编译器 gnueabi、none-eabi、arm-eabi、gnueabihf、gnueabi 的区别

命名规则 交叉编译工具链的命名规则为:arch-vendor-os-(gnu)eabi arch - 体系架构,如 ARM,MIPS vendor - 工具链提供商 os - 目标操作系统 eabi - 嵌入式应用二进制接口(Embedded Application Binary Interface) 根据对操作系统的支持与否,ARM GCC 可分为支持和不支持操作系统,如: arm-none-eabi:这个是没有操作系统的,自然不可能支持那些跟操作系统关系密切的函数,比如 fork。它使用的是 newlib 这个专用于嵌入式系统的 C 库。 arm-none-linux-eabi:用于 Linux 的,使用 Glibc 命名实例 1. arm-none-eabi-gcc (ARM architecture,no vendor,not target an operating system,complies with the ARM EABI) 用于编译 ARM 架构的裸机系统(包括 ARM Linux 的 boot、kernel,不适用编译 Linux 应用 Application),一般适合 ARM7、Cortex-M 和 Cortex-R 内核的芯片使用,所以不支持那些跟操作系统关系密切的函数,比如 fork,他使用的是 newlib 这个专用于嵌入式系统的 C 库。 2. arm-none-linux-gnueabi-gcc (ARM architecture, no vendor, creates binaries that run on the Linux operating system, and uses the GNU EABI) 主要用于基于 ARM 架构的 Linux 系统,可用于编译 ARM 架构的 u-boot、Linux 内核、Linux 应用等。arm-none-linux-gnueabi 基于GCC,使用 Glibc 库,经过 Codesourcery 公司优化过推出的编译器。arm-none-linux-gnueabi-xxx 交叉编译工具的浮点运算非常优秀。一般 ARM9、ARM11、Cortex-A 内核,带有 Linux 操作系统的会用到。 3. arm-eabi-gcc Android ARM 编译器。 4. armcc ARM 公司推出的编译工具,功能和 arm-none-eabi 类似,可以编译裸机程序(u-boot、kernel),但是不能编译 Linux 应用程序。armcc 一般和 ARM 开发工具一起,Keil MDK、ADS、RVDS 和 DS-5 中的编译器都是 armcc,所以 armcc 编译器都是收费的。 5. arm-none-uclinuxeabi-gcc 和 arm-none-symbianelf-gcc arm-none-uclinuxeabi 用于 uCLinux,使用 Glibc。 arm-none-symbianelf 用于 Symbian,没用过,不知道 C 库是什么 。 ABI 和 EABI ABI:二进制应用程序接口(Application Binary Interface (ABI) for the ARM Architecture)。在计算机中,应用二进制接口描述了应用程序(或者其他类型)和操作系统之间或其他应用程序的低级接口。 EABI:嵌入式 ABI。嵌入式应用二进制接口指定了文件格式、数据类型、寄存器使用、堆积组织优化和在一个嵌入式软件中的参数的标准约定。开发者使用自己的汇编语言也可以使用 EABI 作为与兼容的编译器生成的汇编语言的接口。 两者主要区别是,ABI 是计算机上的,EABI 是嵌入式平台上(如 ARM,MIPS 等)。 arm-linux-gnueabi-gcc 与 arm-linux-gnueabihf-gcc 两个交叉编译器分别适用于 armel 和 armhf 两个不同的架构,armel 和 armhf 这两种架构在对待浮点运算采取了不同的策略(有 FPU 的 ARM 才能支持这两种浮点运算策略)。 其实这两个交叉编译器只不过是 gcc 的选项 -mfloat-abi 的默认值不同。gcc 的选项 -mfloat-abi 有三种值 soft、softfp、hard(其中后两者都要求 ARM 里有 FPU 浮点运算单元,soft 与后两者是兼容的,但 softfp 和 hard 两种模式互不兼容): soft: 不用 FPU 进行浮点计算,即使有 FPU 浮点运算单元也不用,而是使用软件模式。 softfp: armel 架构(对应的编译器为 arm-linux-gnueabi-gcc)采用的默认值,用 FPU 计算,但是传参数用普通寄存器传,这样中断的时候,只需要保存普通寄存器,中断负荷小,但是参数需要转换成浮点的再计算。 hard: armhf 架构(对应的编译器 arm-linux-gnueabihf-gcc)采用的默认值,用 FPU 计算,传参数也用 FPU 中的浮点寄存器传,省去了转换,性能最好,但是中断负荷高。 把以下测试使用的 C 文件内容保存成 mfloat.c: #include <stdio.h> int main(void) { double a, b, c; a = 23.543; b = 323.234; c = b / a; printf("the 13/2 = %f\n", c); printf("hello world !\n"); return 0; } 1、使用 arm-linux-gnueabihf-gcc 编译,使用 -v 选项以获取更详细的信息: # arm-linux-gnueabihf-gcc mfloat.c -v ... COLLECT_GCC_OPTIONS='-v' '-mfloat-abi=hard' '-mtls-dialect=gnu' '-mthumb' '-mlibarch=armv7-a+fp' '-march=armv7-a+fp' '-dumpdir' 'a.' 可看出使用了 hard 硬件浮点模式。 2、使用 arm-linux-gnueabi-gcc 编译: # arm-linux-gnueabi-gcc -v mfloat.c -mfloat-abi=softfp ... COLLECT_GCC_OPTIONS='-v' '-mfloat-abi=softfp' '-mtls-dialect=gnu' '-marm' '-mlibarch=armv5t' '-march=armv5t' '-dumpdir' 'a.' 可看出使用 softfp 模式。 我测试用的 GCC 版本是 11.4.0,arm-linux-gnueabihf-gcc 只支持 -mfloat-abi=hard,而 arm-linux-gnueabi-gcc 则支持 -mfloat-abi=soft 与 -mfloat-abi=softfp 两种模...

ARM 交叉编译工具链

交叉编译 交叉编译通俗地讲就是在一种平台上编译出能运行在体系结构不同的另一种平台上的程序,比如在 PC 平台(X86 CPU)上编译出能运行在以 ARM 为内核的 CPU 平台上的程序,编译得到的程序在 X86 CPU 平台上是不能运行的,必须放到 ARM CPU 平台上才能运行,虽然两个平台用的都是 Linux 系统。 交叉编译工具链是一个由编译器、连接器和解释器组成的综合开发环境,交叉编译工具链主要由 binutils、gcc 和 glibc 三个部分组成。有时出于减小 libc 库大小的考虑,也可以用别的 c 库来代替 glibc,例如 uClibc、dietlibc 和 newlib。建立交叉编译工具链是一个相当复杂的过程,如果不想自己经历复杂繁琐的编译过程,网上有一些编译好的可用的交叉编译工具链可以下载,但就以 学习为目的来说读者有必要学习自己制作一个交叉编译工具链(目前来看,对于初学者没有太大必要自己交叉编译一个工具链)。 分类和说明 从授权上,分为免费授权版和付费授权版。 免费版目前有三大主流工具商提供,第一是 GNU(提供源码,自行编译制作),第二是 Codesourcery,第三是 Linora。 arm-none-linux-gnueabi-gcc:是 Codesourcery 公司(目前已经被 Mentor 收购)基于 GCC 推出的的 ARM 交叉编译工具。可用于交叉编译 ARM(32位)系统中所有环节的代码,包括裸机程序、u-boot、Linux kernel、filesystem 和 App 应用程序。 arm-linux-gnueabihf-gcc:是由 Linaro 公司基于 GCC 推出的的 ARM 交叉编译工具。可用于交叉编译 ARM(32位)系统中所有环节的代码,包括裸机程序、u-boot、Linux kernel、filesystem 和 App 应用程序。 aarch64-linux-gnu-gcc:是由 Linaro 公司基于 GCC 推出的的 ARM 交叉编译工具。可用于交叉编译 ARMv8 64 位目标中的裸机程序、u-boot、Linux kernel、filesystem 和 App 应用程序。 arm-none-elf-gcc:是 Codesourcery 公司(目前已经被 Mentor 收购)基于 GCC 推出的的 ARM 交叉编译工具。可用于交叉编译ARM MCU(32位)芯片,如 ARM7、ARM9、Cortex-M/R 芯片程序。 arm-none-eabi-gcc:是 GNU 推出的的ARM交叉编译工具。可用于交叉编译 ARM MCU(32位)芯片,如 ARM7、ARM9、Cortex-M/R 芯片程序。 收费版有 ARM 原厂提供的 armcc、IAR 提供的编译器等等,因为这些价格都比较昂贵,不适合学习用户使用,所以不做讲...

Qt 5.9 静态编译笔记

静态编译 使用 Windows 系统 1、安装环境要求: Supported compiler (Visual Studio 2012 or later, MinGW-builds gcc 4.9 or later) Perl version 5.12 or later http://www.activestate.com/activeperl/ Python version 2.7 or later http://www.activestate.com/activepython/ Ruby version 1.9.3 or later http://rubyinstaller.org/ 2、确保环境变量 Path 中已经加入 Python 、Per、Ruby、D:\Qt\Qt5.9.0\Tools\mingw530_32\bin 的路径。 配置 configure -opensource -confirm-license -static -release \ -platform win32-g++ \ -prefix "D:\Qt\qt_5.9.0_mingw32_static_kits" \ -no-opengl \ -no-openssl \ -nomake tools \ -nomake examples \ -nomake tests \ -qt-freetype \ -qt-libpng \ -qt-libjpeg \ -qt-sqlite \ -qt-pcre \ -qt-zlib \ -skip qt3d \ -skip qtactiveqt \ -skip qtandroidextras \ -skip qtcanvas3d \ -skip qtcharts \ -skip qtconnectivity \ -skip qtdatavis3d \ -skip qtdeclarative \ -skip qtdoc \ -skip qtgamepad \ -skip qtgraphicaleffects \ -skip qtimageformats \ -skip qtlocation \ -skip qtmacextras \ -skip qtmultimedia \ -skip qtnetworkauth \ -skip qtpurchasing \ -skip qtquickcontrols \ -skip qtquickcontrols2 \ -skip qtremoteobjects \ -skip qtscript \ -skip qtscxml \ -skip qtsensors \ -skip qtspeech \ -skip qtsvg \ -skip qttools \ -skip qttranslations \ -skip qtvirtualkeyboard \ -skip qtwebchannel \ -skip qtwebengine \ -skip qtwebsockets \ -skip qtwebview \ -skip qtwinextras \ -skip qtx11extras \ -skip qtxmlpatterns \ -no-feature-dbus -skip 选项可以排除 Qt 标准库(standard repository)之外的子模组(Git Submodule),子模组名就是源码目录中对应的目录名。有些子模组会包含多个模块(Qt modules),比如说 qtconnectivity 子模组就包含了 Qt NFC 模块和 Qt Bluetooth 模块。 -feature-<feature> and -no-feature-<feature> 选项用于包含与排除 Qt 基础库(qtbase 库)的特征。qtbase/src/corelib/global/qfeatures.txt 文件中列出了所有的特征。 -qt-<library>、-system-、-no-<library> 选项用于选择使用源码中自带的还是系统提供的第三方库(third-party libraries),或者都不使用。这些第三方库位于 qtbase/src/3rdparty 编译 mingw32-make -j 4 安装 mingw32-make install 修改连接选项 D:\Qt\qt_5.9.0_mingw32_static_kits\mkspecs\win32-g++\qmake.conf 加入 QMAKE_LFLAGS = -static 或 修改 QMAKE_LFLAGS_RELEASE = -Wl,-s 为 QMAKE_LFLAGS_RELEASE = -Wl,-s -static 或 在工程文件中加入 QMAKE_LFLAGS = -static 通过实验来看应该不用修改 QMAKE_LFLAGS_DLL 的值为 -static,暂时还不了解 QMAKE_LFLAGS_DLL 的用途(估计是指链接生成 dll 文件时用的)。 有些时候还需要配置 qt.conf 如果编译好的 Qt 库的存放位置发生了变化(与 -prefix 参数所指定的不同),则 Qt Versions 提示“Qt没有被正确安装,请运行make install”,解决方法使在 qmake.exe 目录创建 qt.conf,内容为: [paths] prefix = D:/Qt/qt_5.9.0_mingw32_static_kits #当前的实际路径 在 Qt Creator 中配置 注意事项 从 Qt 5.7 开始,已经不支持 Windows XP 平台了,运行程序会提示找不到 dwmapi.dll 。如果编译后的程序需要在 XP 系统上使用,需要使用 Qt 5.6 编...