天天看點

(轉)移植QT5.6到嵌入式開發闆PATH=”/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/work/tools/gcc-3.4.5-glibc-2.3.6/bin”//注釋

原文位址:http://blog.csdn.net/lizuobin2/article/details/52673494

原文如下:

目前網上的大多數 QT 移植教程還都停留在 qt4.8 版本,或者還有更老的 Qtopia ,但是目前 Qt 已經發展到最新的 5.7 版本了,我個人也已經使用了很長一段時間的 qt5.6 for windows ,本文就來介紹一下QT在嵌入式環境的搭建。

移植以到 JZ2440 為例,使用韋老大提供的 ubuntu9.10 虛拟機作為移植環境。當然,其它虛拟機也是可以的,我同樣在 ubuntu14.04 移植成功,隻不過需要額外裝一些庫,後面我會簡單提及。

此外,我嘗試使用 4.3.2 版本的交叉編譯工具編譯 Qt5.6 ,編譯過成功很多錯誤,編譯成功之後使用 qt 編譯應用程式時也存在問題,是以我是用的是友善提供的 4.4.3 版本的交叉編譯工具。建議新手使用與我相同的編譯環境。

因為我們更換了編譯工具,是以,我們有接下來的4個工作。

1、重新編譯核心

2、制作檔案系統

3、移植tslib

4、移植qt

教程涉及的資料:

1、交叉編譯器

arm-linux-gcc-4.4.3.tar.gz .連結:http://pan.baidu.com/s/1nvJF8ud 密碼:oi57

2、針對于 JZ2440 的核心更新檔以及源碼

linux-2.6.22.6.tar.bz2 .連結:http://pan.baidu.com/s/1gf0oZn1 密碼:jrp6

linux-2.6.22.6_jz2440.patch 連結:http://pan.baidu.com/s/1c1CWgTE 密碼:uwuu

4.3寸LCD_mach-smdk2440.c 連結:http://pan.baidu.com/s/1boZsKwf 密碼:1xml

3、busybox

busybox-1.22.1.tar.bz2 .連結:http://pan.baidu.com/s/1cee6CI .密碼:lv81

4、tslib .

tslib-1.4.tar.gz

5、qt5.6 源碼 連結:http://pan.baidu.com/s/1jINj3IQ 密碼:6kkc

qt-everywhere-opensource-src-5.6.0.tar.gz 連結:http://pan.baidu.com/s/1kVnV9oN 密碼:r7cm

一、更換交叉編譯器

首先,将下載下傳好的檔案全部放在 /work 目錄下

1、解壓交叉編譯器

sudo tar zxvf arm-linux-gcc-4.4.3.tar.gz -C / #展開在根目錄

ls /opt/FriendlyARM/toolschain/4.4.3/bin #檢查是否生成了編譯目錄

2、設定環境變量

sudo vi /etc/environment

将現在原有的交叉編譯器路徑替換為我們新解壓的交叉編譯器,舉例:

PATH=”/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/work/tools/gcc-3.4.5-glibc-2.3.6/bin”//注釋

PATH=”/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin:/usr/games:/opt/FriendlyARM/toolschain/4.4.3/bin” //增加

後期測試時我發現這裡是有問題的,由于我的安裝目錄都指定的是 usr 目錄,需要 root 權限,然而在 environment 中設定的環境變量導緻使用 root 權限 make install 過程中出現了個别的 command not found ,于是我将環境變量放到了 /etc/profile 中,這個檔案是對所有使用者生效的。至于environment 百度了一下是系統環境變量按說應該沒問題,但是的确出現了問題。索性還是大家還是直接搞到 profile 中吧。

3、重新開機虛拟機

4、檢查是否更換成功

arm-linux-gcc -v

如圖,更換完畢,我們的編譯器就變為 4.4.3 版本了。

二、重新編譯核心

如果你不是jz2440也沒關系,使用你曾經移植好的核心,重新編譯即可,注意核心需要開啟EABI的支援,如果你是jz2440,按照下面的步驟操作即可。

1、解壓

tar jxvf linux-2.6.22.6.tar.bz2

2、打更新檔

cd linux-2.6.22.6

patch -p1 < ../linux-2.6.22.6_jz2440.patch

如果你是 4.3 寸的 JZ2440 ,替換 LCD 驅動,3.5寸跳過此步

mv ../4.3寸LCD_mach-smdk2440.c arch/arm/mach-s3c2440/mach-smdk2440.c

3、配置核心支援 EABI

make menuconfig

kernel features->

<*>use the arm eabi to …. //選中這一項

4、修改 makefile ,不改的話 4.4.3 編譯器編譯時會報錯

vi Makefile

由于友善在制作這款交叉編譯工具時指定了最低核心版本(2.6.32.2)的限制,是以我們如果不加修改直接編譯啟動核心時會出現 kernel too old 的錯誤資訊,無法啟動。這裡使用一個投機取巧的辦法,強制對 2.6.22.6 核心的版本進行修改,更改核心版本号對核心編譯是有影響的,真正移植的時候還是建議選擇高版本核心。

Makefile 最開始的地方就是版本号:

VERSION = 2

PATCHLEVEL = 6

SUBLEVEL = 22

EXTRAVERSION = .6

中的 SUBLEVEL = 22 改為 SUBLEVEL = 32

//找到一下幾行 ,這裡是因為 4.4.3 的編譯器不支援 gdwarf2 這個選項

ifdef CONFIG_DEBUG_INFO

CFLAGS += -g

AFLAGS += -gdwarf2

endif

//注釋掉 AFLAGS += -gdwarf2

5、編譯

make uImage -j4

編譯完的uImage 在 /arch/arm/boot 目錄下

三、制作檔案系統

1、解壓

tar jxvf busybox-1.22.1.tar.bz2

2、配置

make menuconfig

Busybox Settings ->

general configuration ->

[*] don’t use /usr //選中它 否則會破壞虛拟機

build options->

cross comliler prefix = arm-linux- //選擇交叉編譯工具

installtion options->

busybox installation prefix = /work/my_rootfs //指定安裝路徑

3、編譯&安裝

mkdir -p /work/my_rootfs //安裝路徑

make

make install

cd /work/my_rootfs

ls //檢視是否安裝成功

編譯安裝完畢之後,我們的檔案系統就生成在 /work/my_roofs 目錄下了

4、建立 /etc/inittab

mkdir -p /work/my_rootfs/etc

vi /work/my_rootfs/etc/inittab

# /etc/inittab

# 啟動腳本/etc/init.d/rcS

::sysinit:/etc/init.d/rcS

# 啟動 shell

::askfirst:-/bin/sh

# 重新開機關機前 解除安裝檔案系統

::ctrlaltdel:/sbin/reboot

::shutdown:/bin/umount -a -r

5、建立 /etc/init.d/rcS

mkdir -p /work/my_rootfs/etc/init.d

vi /work/my_rootfs/etc/init.d/rcS

# 這是一個腳本檔案,用/bin/sh解析

#!/bin/sh

# 挂載檔案系統

mount -a

# 使用記憶體檔案系統

mkdir /dev/pts

mount -t devpts devpts /dev/pts

echo /sbin/mdev > /proc/sys/kernel/hotplug

mdev -s

# 設定IP

#/sbin/ifconfig eth0 192.168.1.17 #nfs不需要

# 挂載 /etc/fstab 中的檔案系統

mount -a

exec /etc/rc.local

6、建立rc.local

vi /work/my_rootfs/etc/rc.local

#!/bin/sh

. /etc/profile //注意.後邊有個空格!

7、建立/etc/fstab

vi /work/my_rootfs/etc/fstab

# device mount-point type options dump fsck order

proc /proc proc defaults 0 0

sysfs /sys sysfs defaults 0 0

tmpfs /tmp tmpfs defaults 0 0

tmpfs /dev tmpfs defaults 0 0

8、建構 /dev 目錄

mkdir -p /work/my_rootfs/dev

cd /work/my_rootfs/dev

sudo mknod console c 5 1

sudo mknod null c 1 3

9、建立其它目錄

mkdir proc mnt tmp sys root usr

10、拷貝Lib

cd /opt/FriendlyARM/toolschain/4.4.3/arm-none-linux-gnueabi/lib

cp .so /work/my_rootfs/lib -d

cd /opt/FriendlyARM/toolschain/4.4.3/lib

cp .so /work/my_rootfs/lib -d

四、移植 tslib

1、解壓&配置&編譯

如果不是使用的韋老大的虛拟機可能還需要安裝一下幾個包 autoconf automake libtool

#sudo apt-get install autoconf automake libtool

tar zxvf tslib-1.4.tar.gz

sudo mkdir -p /usr/local/tslib

cd tslib

./autogen.sh

./configure –host=arm-linux ac_cv_func_malloc_0_nonnull=yes CC=arm-none-linux-gnueabi-gcc CXX=arm-none-linux-gnueabi-g++ -prefix=/usr/local/tslib

make

sudo make install

如果編譯過程中遇到 undefined reference to ‘rpl_malloc’,前面配置完成之後修改 config.h.in 檔案,注釋掉檔案最後的 #undef malloc ,重新 make 即可。

安裝完成之後,tslib 就安裝在虛拟機 /usr/local/tslib 目錄下

2、更改 tslib 配置檔案

cd /usr/local/tslib/etc/

sudo vi ts.conf

去掉# module_raw input 前面的 “#” 和空格

3、将制作好的 tslib 移動到我們制作的檔案系統

cd /usr/local

sudo tar zcvf tslib.tar.gz tslib

mkdir -p /work/my_rootfs/usr/local

cp tslib.tar.gz /work/my_rootfs/usr/local

tar zxvf tslib.tar.gz

rm tslib.tar.gz

4、添加 tslib 環境變量

vi /work/my_rootfs/etc/profile

#!/bin/sh

export T_ROOT=/usr/local/tslib

export LD_LIBRARY_PATH=/usr/local/tslib/lib: LDLIBRARYPATHexportTSLIBCONSOLEDEVICE=noneexportTSLIBFBDEVICE=/dev/fb0exportTSLIBTSDEVICE=/dev/input/event0exportTSLIBPLUGINDIR= T_ROOT/lib/ts

export TSLIB_CONFFILE=$T_ROOT/etc/ts.conf

export POINTERCAL_FILE=/etc/pointercal

export TSLIB_CALIBFILE=/etc/pointercal

此時,tslib 就已經移植好了,你可以挂載 nfs 檔案系統啟動,cd /usr/local/tslib/bin

./ts_test 來測試

按照教程制作應該沒有問題,我在使用高版本核心的時候遇到“selected device is not a touchscreen I understand”錯誤,百度了一下,是由于核心和編譯器的一個宏定義不一緻導緻的,vi include/Linux/input.h EV_VERSION 為 0x0100000 ,從新編譯核心特别是觸摸驅動。

五、移植 qt5.6

1、解壓

tar zxvf qt-everywhere-opensource-src-5.6.0.tar

2、修改編譯配置

cd /work/qt-everywhere-opensource-src-5.6.0/qtbase/mkspecs/linux-arm-gnueabi-g++

vi qmake.conf

針對于 2440 增加:

QT_QPA_DEFAULT_PLATFORM = linuxfb

QMAKE_CFLAGS += -msoft-float -D__GCC_FLOAT_NOT_NEEDED -march=armv4t -mtune=arm920t

QMAKE_CXXFLAGS += -msoft-float -D__GCC_FLOAT_NOT_NEEDED -march=armv4t -mtune=arm920t

march 指的 cpu 架構,針對 2440 來說是 armv4t

mtune 指的 cpu 名字,針對 2440 來說是 arm920t

如果你是 A8 的闆子 ,可以參考下邊的配置

QT_QPA_DEFAULT_PLATFORM = linuxfb

QMAKE_CFLAGS += -msoft-float -D__GCC_FLOAT_NOT_NEEDED -march=armv7-a -mtune=cortex-a8

QMAKE_CXXFLAGS += -msoft-float -D__GCC_FLOAT_NOT_NEEDED -march=armv7-a -mtune=cortex-a8

如果你是 A9 的闆子 ,可以參考下邊的配置

QT_QPA_DEFAULT_PLATFORM = linuxfb

QMAKE_CFLAGS += -msoft-float -D__GCC_FLOAT_NOT_NEEDED -march=armv7-a -mtune=cortex-a9

QMAKE_CXXFLAGS += -msoft-float -D__GCC_FLOAT_NOT_NEEDED -march=armv7-a -mtune=cortex-a9

将以下部分

# modifications to g++.conf

QMAKE_CC = arm-linux-gnueabi-gcc

QMAKE_CXX = arm-linux-gnueabi-g++

QMAKE_LINK = arm-linux-gnueabi-g++

QMAKE_LINK_SHLIB = arm-linux-gnueabi-g++

# modifications to linux.conf

QMAKE_AR = arm-linux-gnueabi-ar cqs

QMAKE_OBJCOPY = arm-linux-gnueabi-objcopy

QMAKE_NM = arm-linux-gnueabi-nm -P

QMAKE_STRIP = arm-linux-gnueabi-strip

修改為:-lts 是指在連結時連結 tslib 庫

# modifications to g++.conf

QMAKE_CC = arm-none-linux-gnueabi-gcc -lts

QMAKE_CXX = arm-none-linux-gnueabi-g++ -lts

QMAKE_LINK = arm-none-linux-gnueabi-g++ -lts

QMAKE_LINK_SHLIB = arm-none-linux-gnueabi-g++ -lts

# modifications to linux.conf

QMAKE_AR = arm-none-linux-gnueabi-ar cqs

QMAKE_OBJCOPY = arm-none-linux-gnueabi-objcopy

QMAKE_NM = arm-none-linux-gnueabi-nm -P

QMAKE_STRIP = arm-none-linux-gnueabi-strip

3、配置編譯

sudo mkdir -p /usr/local/Qt5.6

cd ../../../

./configure -prefix /usr/local/Qt5.6 \

-opensource \

-release \

-confirm-license \

-xplatform linux-arm-gnueabi-g++ \

-shared \

-qt-zlib \

-no-gif \

-qt-libjpeg \

-no-nis \

-no-opengl \

-no-cups \

-no-glib \

-no-dbus \

-no-rpath \

-no-sse2 -no-sse3 -no-ssse3 -no-sse4.1 -no-sse4.2 \

-no-avx \

-no-openssl \

-nomake tools \

-qreal float \

-qt-libpng \

-tslib \

-nomake examples \

-I /usr/local/tslib/include \

-L /usr/local/tslib/lib

make -j4

sudo make install

如果使用的不是韋老大的虛拟機編譯過程中可能報關于libxcb的錯誤,檢視 qtbase/src/plugins/platforms/xcb 底下的 readme 安裝相應的庫就可以了。

4、将移植好的 qt 打包到開發闆

cd /usr/local

sudo tar zcvf Qt5.6.tar.gz Qt5.6

cp Qt5.6.tar.gz /work/my_rootfs/usr/local/

tar zxvf Qt5.6.tar.gz

rm Qt5.6.tar.gz

rm -r doc include bin mkspecs qml translations

5、設定qt相關的環境變量

此部分可以參考qt官方問文檔:http://doc.qt.io/qt-5/embedded-linux.html ,這我這僅僅是設定支援了觸摸屏,你可以參考官方設定支援鍵盤,滑鼠等等。

在檔案系統 /etc/profile 裡添加

export QTEDIR=/usr/local/Qt5.6

export LD_LIBRARY_PATH=/usr/local/Qt5.6/lib: LDLIBRARYPATHexportQTQPAGENERICPLUGINS=tslibexportQTQPAFONTDIR= QTEDIR/lib/fonts

export QT_QPA_PLATFORM_PLUGIN_PATH=$QTEDIR/plugins

export QT_QPA_PLATFORM=linuxfb:fb=/dev/fb0:size=480x272:mmSize=480x272:offset=0x0:tty=/dev/tty1

export QT_QPA_FB_TSLIB=1

紅色部分請根據自己的開發闆進行修改,我手頭的開發闆是 3.5 寸 320*240 的 LCD,JZ2440 V3 用上面的參數即可。

此時,qt 已經移植完畢,你可以打包放入你的 nfs 目錄啟動進行測試了,至于制作 yaffs2 jffs2 等檔案系統請參考:http://blog.csdn.net/lizuobin2/article/details/52589215 ,qt庫比較大,燒錄的時候可能比較困難,可以先将QT去除,打包成檔案系統大約之後20M不到,燒錄到開發闆之後,啟動核心,通過nfs tftp等工具,再将打包好的Qt傳到闆子上展開即可。

六、測試Qt應用程式

我個人習慣先用 windows 版本的 qt 寫好程式,調試沒問題之後直接拿到虛拟機上編譯,windows 版本的 qt 安裝非常簡單,就跟安裝個QQ一樣毫不費力,這裡就不再贅述了。

将windows下編輯好的源碼拷貝到虛拟機上,切換到源碼目錄

/usr/local/Qt5.6/bin/qmake

make

即可生成可執行檔案,拿到開發闆測試即可。

嫌費事的話,将 qmake 添加到環境變量裡。

在測試過程中我發現程式跑起來沒問題,但是有以下兩條錯誤資訊:

QIconvCodec::convertFromUnicode: using Latin-1 for conversion, iconv_open failed

QIconvCodec::convertToUnicode: using Latin-1 for conversion, iconv_open failed

大概是缺少 libiconv

下載下傳 連結:http://pan.baidu.com/s/1c22xb4O 密碼:pbld

mkdir -p /usr/local/libiconv

./configure –host=arm-none-linux-gnueabi –prefix=/usr/local/libiconv CC=arm-none-linux-gnueabi-gcc LDFLAGS=”-L/opt/FriendlyARM/toolschain/4.4.3/arm-none-linux-gnueabi/sys-root/lib” –enable-static

make

sudo make install

把安裝目錄/lib 下的 preloadable_libiconv.so 檔案系統的 /lib 下, 在 /etc/profile 中添加

export LD_PRELOAD=/lib/preloadable_libiconv.so

7、使Qt支援中文

在測試過程中很悲劇的發現移植好的qt不支援中文,強大度娘給了我答案。

下載下傳字庫 連結:http://pan.baidu.com/s/1bp9QFQv 密碼:2u81

将DroidSansFallback.ttf 放到檔案系統 /usr/local/Qt5.6/lib/fonts 目錄下,雖然Qt自帶了很多字庫了,但是都沒有中文的。

然後在使用qt creator 開發qt應用程式時,在項目中添加

QT += gui

包含頭檔案 #include

代碼中設定使用的字型。

int id = QFontDatabase::addApplicationFont(“/usr/local/Qt5.6/lib/fonts/DroidSansFallback.ttf”);

QString msyh = QFontDatabase::applicationFontFamilies (id).at(0);

QFont font(msyh,10);

font.setPointSize(20);

this->setFont(font);

8、制作好的檔案系統&核心

8.1 簡單的qt例子,代碼中Ui尺寸寫死為 320*240 ,如果不适合你的闆子請修改。

連結:http://pan.baidu.com/s/1qXV4C1Y 密碼:908q

8.2 jz2440 核心(包含3.5和4.3)

連結:http://pan.baidu.com/s/1qYMrxmc 密碼:qsk0

8.3 檔案系統

連結:http://pan.baidu.com/s/1skLtj3J 密碼:lbo2

改檔案系統沒有打包成鏡像,請使用nfs啟動,解壓之後在 dev 目錄建立 console null 裝置節點。

此外,/etc/profile 環境變量中的參數請修改成符合自己開發闆的參數,預設為3.5寸。

解壓縮之後80多M,制作成 yaffs 恐怕會過 100 M,qt的庫檔案沒有進行剪裁,需要制作鏡像的同學可以進行剪裁(檢視你的app依賴于哪些庫,其餘的都可以去掉)。

8.4 編譯好的Qt

連結:http://pan.baidu.com/s/1pLCznr9 密碼:l6pz

9、最新的uboot、核心、檔案系統

文章寫了很久了,感謝有衆多朋友的信任,參考本文進行了一系列的嘗試,在此過程中也發現了文章中的不足,以及網盤中檔案系統中的一些不足,恰巧最近有機會,重新做了一份核心,檔案系統,以及配套的 uboot,并将它們放在了github上持續更新。如有需要,請下載下傳:

注意:編譯器版本:4.4.3

rootfs:

https://github.com/lizuobin/rootfs_jz2440.git

注意:git 下來之後 /dev目錄沒有 console 和 null 節點,請參考前面建立這兩個裝置節點

這個檔案系統相對完善,開機會自動校準(第一次),然後運作一個簡單的Qt桌面程式,暫時沒有放其它應用程式。檔案系統中已經帶有ftpserver工具,大家可以使用filezila進行檔案傳輸,加密方式選擇(僅ftp…不安全),端口21,使用者root,沒有密碼。檔案系統龐大,還是建議先将qt等一些東西拷貝出來再傳進去。

核心:https://github.com/lizuobin/linux-3.4.2-jz2440.git

記得:cp config_ok .config

uboot:https://github.com/lizuobin/uboot-2012.04.01-jz2440.git

如果你想讓你的開發闆支援 ssh 請參考:

http://blog.csdn.net/lizuobin2/article/details/52664339

如果你想讓你的開發闆支援序列槽(rz)傳輸檔案請參考:

http://blog.csdn.net/lizuobin2/article/details/52601617

如果你想讓你的開發闆想虛拟機一樣在指令行顯示使用者名請參考:

http://blog.csdn.net/lizuobin2/article/details/52664657

嵌入式QT相關的設計開發需求,請聯系我QQ:271526143

繼續閱讀