1. 程式人生 > >buildroot之交叉編譯環境

buildroot之交叉編譯環境

轉載:

前言:

    為了搭建交叉編譯環境,查了很多的方法,有自己搭建的(高手),有的用cross-ng工具的等等,最後查到了buildroot這個工具,最後為啥選擇這個工具的原因是buildroot不僅能搭建交叉編譯環境,而且還能編譯核心,根檔案系統,可見功能的強大,但是第一次用這個工具還是出現各種各樣的問題,所以這回要詳細的說明buildroot搭建交叉編譯器的使用方法並且解釋出現的問題,雖然操作簡化了很多,但是還是會出現很多的問題,廢話不多說,進入主題

目標平臺:

system type : Ralink MT7620A ver:2 eco:6
machine       : AWF-5G
processor     : 0
cpu model    : MIPS 24KEc V5.0
isa                : mips1 mips2 mips32r1 mips32r2

linux version : 3.10.44

buidRoot版本:

當然是最新版本 buildroot-2016.08.tar.gz, buildroot版本更新頻率還是蠻高的,一般3個月一更新,因為我是在9月份研究這個buildroot,所以就用的這個版本,下載網址:

https://buildroot.org/download

具體操作:

1.將buildroot解壓後,我們的第一步是建立預設配置, 首先檢視一下目錄下的list

buildroot為了方便使用者使用, 提前配置好了很多平臺的配置, 在configs資料夾裡, 

我們發現有好多的配置資訊,因為我們的目標平臺是mip32的, 所以選擇了qemu_mips32r2el_malta_defconfig這個配置, 細心的讀者還會發現下面還有一個qemu_mips32r2的配置,區別是前者多了個“el”, 其實帶el的意思是小端,因為我的目標平臺是小端,所以選了這個配置

2. 在終端輸入 make menuconfig 進一步配置,輸入後會出現如下介面

因為我們的目的只是建立交叉編譯環境,所以只用到了上面紅色框框的選擇項,他們的意義如下(儘可能大白話解釋)

Target option:  選擇目標平臺, 大端小端等等, 目的是選擇gcc的種類(編譯出對應平臺的可執行檔案)

Buid options:   這個選項可厲害了,  裡面有個選項可以配置編譯後的交叉編譯器的路徑, 這個選項我吃了大虧, 在後面細說

ToolChain:  用於配置gcc所需要的版本,還有一些依賴的工具, 配置一個工具鏈,需要以下部分與工具

    ---Binutils : 編譯連結需要的一些工具,比如ld,ar等

    ---Kernel headers:編譯的c庫需要與核心訪問時, 需要標頭檔案

    ---c/c++ libraries

    ---Gcc compiler

    ---GDB debugger(optional)

Target packages: 這個就不用說,太爽了,比如,想弄個sqlite移植到目標平臺, 裡面就有啦

3.接下來一個一個選項進去看一下

3.1 Target options

我們可以看到,我們一進到這個畫面這些配置都被選好了,原因是因為之前我們已經配置好了預設選項,所以這樣,  當然我們也可以自己重新選擇

上面非常清楚明確, 目標平臺是MIPS,小端, 最後use soft-float 選上

3.2 Build options

這個選項的話有一個地方要注意一下,就是Host dir, 其餘選項都可忽略,  意思就是編譯出的編譯器的路徑, 這個東西得特別注意一下,因為如果你的編譯工具想在別的機器上用,最好填寫一個共同的路徑/usr/local

原因: 前提我已經編譯好了工具鏈,所以我們看一下gcc的版本,

其中:   --with-sysroot=/usr/local/openWrt_cross/usr/mipsel-openwrt-linux-uclibc/ :--with-sysroot選項的目的是告訴編譯器在編譯obj檔案時所需要庫的路徑

COLLECT_GCC=/usr/local/openWrt_cross/usr/bin/mipsel-linux-gcc.br_real :在gcc編譯obj檔案是會用到這個.br_real,我們看看這個.br_real裡面的資訊吧

我們可以看到 指定的library path: 是/usr/local/openwrt_cross/usr/lib

換句話說我們對HostDir進行了設定,指定的路徑是/usr/loca/openwrt_cross(這個資料夾是手動自己建立的)/, 當對obj進行編譯時,就會根據此路徑去找相應的庫

之前的出錯現象:

我沒有對host dir進行配置,所生成出的編譯環境 會預設生成在路徑/yy/xx/下--->所以對應的庫路徑資訊是/yy/xx/usr/lib

生成好工具鏈後,在自己本地沒問題, 當我把工具鏈打包放到別的PC上實驗時,會出現mipsel-linux-gcc.br_real 找不到 libm.so的錯誤,原因是因為指定的庫資訊路徑是/yy/xx/usr/lib,當然,在別人的PC上不會有/yy/xx的路徑,所以出錯

總結: 如果要實現工具鏈共享(就是放在別的機器上也能用) hostDir這個配置選項好配置好,我覺得一般就是/usr/local/就可以

引用手冊的一句話:

You may want to compile, for your target, your own programs or other software that are not packaged in Buildroot. In order to
do this you can use the toolchain that was generated by Buildroot.
The toolchain generated by Buildroot is located by default in output/host/. The simplest way to use it is to add out
put/host/usr/bin/ to your PATH environment variable and then to use ARCH-linux-gcc, ARCH-linux-objdump,
ARCH-linux-ld, etc.
It is possible to relocate the toolchain - but then --sysroot must be passed every time the compiler is called to tell where the
libraries and header files are.
It is also possible to generate the Buildroot toolchain in a directory other than output/host by using the Build options
! Host dir option. This could be useful if the toolchain must be shared with other users.

3.3Tool chain

上面標號的都是這回我們用到的, 首先

①是選擇工具鏈的種類 1. Buildroot toolchain: 內部工具鏈(因為這回要製作工具鏈,所以選擇這個)  2. External toolchain: 外部工具鏈, 比如你已經有工具鏈了,想作檔案系統, 就選外部工具鏈, 選上之後, 在之後的選項填寫外部工具鏈的路徑

②給編譯後的工具鏈起個名字,這個隨便起

③核心版本號, 這個比較重要, 要選你要執行目標平臺核心版本相符合的版本號, 前面講到,我的目標平臺linux kernel 版本是 3.10.44, 所以這裡選3.10.x的,當然,由於向下相容,所以我也可以選3.10以下的版本都可以

之前出錯的現象:

 預設配置選的是linux 4.x版本的標頭檔案, 之後編譯出工具鏈,用工具鏈生成的可執行檔案在目標平臺執行不了,因為目標平臺的版本是3.10比較低, 所以這裡要注意

引用手冊上的話:

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.

④選擇用到的c庫,這裡有3中選擇,其中常用的是uClib,與gnuLib, uClib是嵌入gnuLib的縮減版本,它比較小(不是每個介面都實現, gunLib是都實現了,所以這個庫比較大),而且現在都支援QT了所以一般大多嵌入式平臺都用這個庫,當然我的目標平臺也是用的這個庫

要注意的是: 當③④選了之後, ⑤⑥⑦會根據③④進行自動匹配版本,如果不是高手的話建議不要改,當然,作為新手的我嘗試改了一下(把⑦中的版本降到了4.8而已,後來實驗不成功又把⑥的版本也降了一下), 工具鏈編譯出來了,編譯出的hello world可執行檔案可以在目標平臺上執行,那麼這就OK了嗎? 當然不是, 如果程式在寫的複雜點,比如加了生成執行緒之類的程式就執行不起來了,所以建議③ ④選定後,⑤⑥⑦就不用在改了

手冊其實也是這麼說的

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.

⑤ 這個選項是選uLibc專用的選項,在之前的buildroot中 這個選項有3個,

---linuxthreads

---linuxthreads (stable/old)

---Native POSIX Threading (NPTL)

老版本的linux 的執行緒庫用的是linuxthreads,用著用著發現有很多不穩定的地方,於是就產生了 NPTL來代替 linuxthreads,所以隨著linux的發展, linuxthreads被淘汰,

現在在當前的版本中乾脆就沒有了,直接就是NPTL了...

⑧ 這個一般也選上會生成g++, 還有Enable RPC support,是支援nfs

3.4Target packages

這個選項就不多說了,很吊, 以後想移植什麼應用,直接去這裡找就可以了,分分鐘生成, 比如一些常用的嵌入式資料庫啊 sql, sqlite redis 都可以輕鬆移植,選上即可

4.配置好之後,make即可, 等3-4個小時就搞定了(我的是50M電信寬頻)

關於buildroot的研究就寫到這裡,之後做根檔案系統什麼的等用到了在說
--------------------- 
作者:loe 
來源:CSDN 
原文:https://blog.csdn.net/mxgsgtc/article/details/53047562 
版權宣告:本文為博主原創文章,轉載請附上博文連結!