文章

qt5.15.2 交叉编译 arm64

qt5.15.2 交叉编译 arm64

该文主要介绍使用 CentOS7 x86_64 交叉编译为 arm64

qt5.15.2 交叉编译 arm64

为了实现代码能够自动化编译成各个 Linux 系统或架构上能够运行的程序,采用 Jenkins 实现自动化部署,考虑到 arm64 实体机编译性能不好以及成本问题,于是就采用交叉编译。

1. 环境

  • 虚拟机系统:CentOS-7-x86_64-DVD-2207-02.iso
  • 交叉编译工具链:gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu.tar.xzsysroot-glibc-linaro-2.21-2017.05-aarch64-linux-gnu.tar.xz
  • Qt:qt-everywhere-src-5.15.2.tar.xz

项目中用到证书以及网页,所以我需要 OpenSSL X11 WebEngine 模块

编译qt core需要4G内存,编译X11需要8G,编译WebEngine至少需要24G,否则会内存耗尽导致退出

2. 准备依赖

2.1. 软件包说明

所有的原始文件都是放在 /cross 目录下

1
2
mkdir /cross
cd /cross
软件包下载地址路径安装路径
gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu.tar.xzhttps://releases.linaro.org/components/toolchain/binaries/5.4-2017.05/aarch64-linux-gnu//cross 
sysroot-glibc-linaro-2.21-2017.05-aarch64-linux-gnu.tar.xzhttps://releases.linaro.org/components/toolchain/binaries/5.4-2017.05/aarch64-linux-gnu//cross/sysroot-aarch64
gcc-5.4.0.tar.gzhttps://mirrors.nju.edu.cn/gnu/gcc/gcc-5.4.0//cross/usr/local/gcc
各种依赖 /cross/dependence/aarch64

2.2. 配置交叉编译环境

gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu 是交叉编译工具链,sysroot-glibc-linaro-2.21-2017.05-aarch64-linux-gnu 是交叉编译目标环境,如果不是通用环境可以参考野火交叉编译 Qt 库文章1

需要做的就是解压以及配置环境变量

1
2
3
4
5
6
7
8
9
10
11
12
13
# 解压
tar -xvf gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu.tar.xz
# 修改环境变量文件
vim /etc/profile
# 添加
export PATH=/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin:$PATH
# 使环境变量文件生效
source /etc/profile

# 解压
tar -xvf sysroot-glibc-linaro-2.21-2017.05-aarch64-linux-gnu.tar.xz
# 移动并改名,为了路径简短
mv sysroot-glibc-linaro-2.21-2017.05-aarch64-linux-gnu /sysroot-aarch64

使用 aarch64-linux-gnu-gcc -v 查看到版本即为配置成功。

2.3. 升级系统 GCC

CentOS7 默认的版本的是 gcc4.8,为了和交叉编译统一,需要升级版本为 gcc5.4

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
# 可能缺失基础 gcc
yum install gcc gcc-c++

# 升级 gcc
tar -xvf gcc-5.4.0.tar.gz
cd gcc-5.4.0
# 自动检查预编译环境并安装,需要联网
./contrib/download_prerequisites
# 安装路径是 /usr/local/gcc
./configure --prefix=/usr/local/gcc --enable-checking=release --enable-languages=c,c++ --disable-multilib
make -j4 && make install

# 修改环境变量文件
vim /etc/profile
# 添加
export PATH=/usr/local/gcc/bin:$PATH
export LD_LIBRARY_PATH=/usr/local/gcc/lib64:$LD_LIBRARY_PATH
# 使环境变量文件生效
source /etc/profile

使用 gcc -v 查看到版本即为配置成功。

2.4. 下载依赖

X11 相关下载网址:https://www.x.org/releases/individual/

文件都放在 /cross/dependence

1
2
mkdir /cross/dependence
cd /cross/dependence

以下是下载 OpenSSL X11 WebEngine 所需要依赖库的脚本 download_dependence.sh,需要联网使用且部分还需要挂代理。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
#!/bin/sh
# openssl
wget -c https://www.openssl.org/source/old/1.1.1/openssl-1.1.1q.tar.gz

# x11 dependence
wget -c https://www.x.org/releases/individual/proto/xorgproto-2020.1.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXrender-0.9.10.tar.gz
wget -c https://www.x.org/releases/individual/lib/xtrans-1.4.0.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXau-1.0.9.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXrender-0.9.10.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXext-1.3.4.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXrandr-1.5.2.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXfixes-5.0.3.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXcomposite-0.4.5.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXcursor-1.2.0.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXi-1.7.10.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXScrnSaver-1.2.3.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXtst-1.2.3.tar.gz
wget -c https://www.x.org/releases/individual/lib/libxshmfence-1.3.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXxf86vm-1.1.4.tar.gz
wget -c https://www.x.org/releases/individual/util/util-macros-1.19.3.tar.gz
wget -c https://www.x.org/releases/individual/data/xkeyboard-config/xkeyboard-config-2.30.tar.gz
wget -c https://www.x.org/releases/individual/lib/libSM-1.2.3.tar.gz
wget -c https://www.x.org/releases/individual/lib/libICE-1.0.10.tar.gz
wget -c https://xkbcommon.org/download/libxkbcommon-1.4.0.tar.xz
wget -c https://dri.freedesktop.org/libdrm/libdrm-2.4.100.tar.gz

# xcb
wget -c https://www.x.org/releases/individual/xcb/libpthread-stubs-0.4.tar.gz
wget -c https://www.x.org/releases/individual/xcb/xcb-util-0.3.9.tar.gz
wget -c https://www.x.org/releases/individual/xcb/xcb-util-image-0.3.9.tar.gz
wget -c https://www.x.org/releases/individual/xcb/xcb-util-keysyms-0.3.9.tar.gz
wget -c https://www.x.org/releases/individual/xcb/xcb-util-wm-0.3.9.tar.gz
wget -c https://www.x.org/releases/individual/xcb/xcb-util-renderutil-0.3.9.tar.gz
wget -c https://www.x.org/releases/individual/xcb/xcb-proto-1.13.tar.gz
wget -c https://www.x.org/releases/individual/xcb/libxcb-1.13.tar.gz

# glib2
wget -c https://www.zlib.net/fossils/zlib-1.2.11.tar.gz
wget -c https://sourceforge.net/projects/pcre/files/pcre/8.45/pcre-8.45.tar.gz
wget -c https://github.com/libffi/libffi/releases/download/v3.3/libffi-3.3.tar.gz
wget -c https://github.com/SELinuxProject/selinux/releases/download/20191204/libsepol-3.0.tar.gz
wget -c https://github.com/SELinuxProject/selinux/releases/download/20191204/libselinux-3.0.tar.gz
wget -c https://ftp.acc.umu.se/pub/GNOME/sources/glib/2.61/glib-2.61.3.tar.xz

# x11
wget -c https://www.x.org/releases/individual/lib/libX11-1.7.5.tar.gz

# webengine
wget -c https://www.x.org/releases/individual/lib/libxkbfile-1.1.0.tar.gz
wget -c https://www.x.org/releases/individual/lib/libXdamage-1.1.5.tar.gz
wget -c https://github.com/libexpat/libexpat/releases/download/R_2_2_9/expat-2.2.9.tar.gz
wget -c https://dbus.freedesktop.org/releases/dbus/dbus-1.13.6.tar.gz
wget -c https://download.savannah.gnu.org/releases/freetype/freetype-2.10.1.tar.gz
wget -c ftp://xmlsoft.org/libxml2/libxml2-2.9.9.tar.gz
wget -c https://nchc.dl.sourceforge.net/project/libuuid/libuuid-1.0.3.tar.gz
wget -c https://www.freedesktop.org/software/fontconfig/release/fontconfig-2.13.92.tar.gz
wget -c https://github.com/sqlite/sqlite/archive/refs/tags/version-3.30.1.tar.gz
wget -c http://www.linuxfromscratch.org/patches/blfs/9.1/nss-3.50-standalone-1.patch
wget -c https://ftp.mozilla.org/pub/security/nss/releases/NSS_3_50_RTM/src/nss-3.50-with-nspr-4.25.tar.gz
wget -c https://gitlab.freedesktop.org/mesa/mesa/-/archive/mesa-19.0.0/mesa-mesa-19.0.0.tar.gz
wget -c https://github.com/unicode-org/icu/releases/download/release-65-1/icu4c-65_1-src.tgz
wget -c https://nodejs.org/download/release/latest-v10.x/node-v10.24.1.tar.gz

2.5. 编译依赖

2.5.1. 前置条件

上述依赖库编译还需要本机编译工具,以下代码是下载需要的编译工具

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
# xkbcommon 编译环境
yum install bison
yum install python3
python3 -m pip install meson
python3 -m pip install ninja
python3 -m pip install mako

# dbus 编译环境
yum install flex
yum install libtool

# nss 编译环境
yum install tcl
yum install patch
yum install zlib-devel
# qt 实际编译需要本地的 nss
yum install nss

# fontconfig 编译环境
yum install gperf

2.5.2. 编译依赖

文件都放在 /cross/dependence

xkbcommon glib mesa 是使用 mesonninja 构建,所以需要编辑 cross-file。可能需要自行更改自己对应文件中编译相关目录。

编辑 aarch64_xkbcommon.txt,内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
[binaries]
c = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-gcc'
cpp = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-c++'
ar = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-ar'
strip = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-strip'
ld = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-ld'
pkgconfig = '/usr/bin/pkg-config'
 
[properties]
pkg_config_libdir = ['/aarch64/lib/pkgconfig', '/aarch64/share/pkgconfig']
skip_sanity_check = true
 
[paths]
libdir = '/aarch64/lib'
includedir = '/aarch64/include'
prefix = '/aarch64'
 
[host_machine]
system = 'linux'
cpu_family = 'arm'
cpu = 'ARM'
endian = 'little'
 
[build_machine]
system = 'linux'
cpu_family = 'x86_64'
cpu = 'i686'
endian = 'little'

编辑 aarch64_glib.txt,内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
[binaries]
c = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-gcc'
cpp = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-c++'
ar = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-ar'
strip = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-strip'
ld = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-ld'
pkgconfig = '/usr/bin/pkg-config'
 
[properties]
pkg_config_libdir = ['/aarch64/lib/pkgconfig', '/aarch64/share/pkgconfig']
skip_sanity_check = true
 
[paths]
libdir = '/aarch64/lib'
includedir = '/aarch64/include'
prefix = '/aarch64'
 
[host_machine]
system = 'linux'
cpu_family = 'arm'
cpu = 'ARM'
endian = 'little'
 
[build_machine]
system = 'linux'
cpu_family = 'x86_64'
cpu = 'i686'
endian = 'little'

编辑 aarch64_mesa.txt,内容如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
[binaries]
c = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-gcc'
cpp = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-c++'
ar = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-ar'
strip = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-strip'
ld = '/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-ld'
pkgconfig = '/usr/bin/pkg-config'
 
[properties]
pkg_config_libdir = ['/aarch64/lib/pkgconfig', '/aarch64/share/pkgconfig']
skip_sanity_check = true
 
[paths]
libdir = '/aarch64/lib'
includedir = '/aarch64/include'
prefix = '/aarch64'
 
[host_machine]
system = 'linux'
cpu_family = 'arm'
cpu = 'ARM'
endian = 'little'
 
[build_machine]
system = 'linux'
cpu_family = 'x86_64'
cpu = 'i686'
endian = 'little'

以下是编译依赖的脚本 aarch64_dependence.sh,直接运行即可

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
396
397
398
399
400
401
402
403
404
405
406
407
408
409
410
411
412
413
414
415
416
417
418
419
420
421
422
423
424
425
426
427
428
429
430
431
432
433
434
435
436
437
438
439
440
441
442
443
444
445
446
447
448
449
450
451
452
453
454
455
456
457
458
459
460
461
462
463
464
465
466
467
468
469
470
471
472
473
474
475
476
477
478
479
480
481
482
483
484
485
486
487
488
489
490
491
492
493
494
495
496
497
498
499
500
501
502
503
504
505
506
507
508
509
510
511
512
513
514
515
516
517
518
519
520
521
522
523
524
525
526
527
528
529
530
531
532
533
534
535
536
537
538
539
540
541
542
543
544
545
546
547
548
549
550
551
552
553
554
555
556
557
558
559
560
561
562
563
564
565
566
567
568
569
570
571
572
573
574
575
576
577
578
579
580
581
582
583
584
585
586
587
588
589
590
591
592
593
594
595
596
597
598
599
600
601
602
603
604
605
606
607
608
#!/bin/sh
set -e

MY_PREFIX=/aarch64
MY_HOST=aarch64-linux-gnu

export PKG_CONFIG_PATH=${MY_PREFIX}/lib/pkgconfig:${MY_PREFIX}/share/pkgconfig
export C_INCLUDE_PATH=${MY_PREFIX}/include:$C_INCLUDE_PATH
export LD_LIBRARY_PATH=${MY_PREFIX}/lib:$LD_LIBRARY_PATH

export CFLAGS="$CFLAGS -I${MY_PREFIX}/include"
export LDFLAGS="$LDFLAGS -L${MY_PREFIX}/lib"
export LDFLAGS="$LDFLAGS -Wl,-rpath-link=${MY_PREFIX}/lib -Wl,-rpath-link=${MY_PREFIX}/lib64"
export LDFLAGS="$LDFLAGS -Wl,-rpath=${MY_PREFIX}/lib -Wl,-rpath=${MY_PREFIX}/lib64"

export CC=${MY_HOST}-gcc
export CXX=${MY_HOST}-g++

build_script_openssl() {
    ./Configure \
        linux-aarch64 \
        --prefix=${MY_PREFIX}

    make -j4 && make install
}

build_script_xcb_common() {
    ./configure \
        --prefix=${MY_PREFIX} \
        --host=${MY_HOST} \
        --enable-option-checking \
        --enable-malloc0returnsnull

    make -j4 && make install
}

build_script_x11() {
    ./configure \
        --prefix=${MY_PREFIX} \
        --host=${MY_HOST} \
        --enable-option-checking \
        --enable-unix-transport \
        --enable-tcp-transport \
        --enable-ipv6 \
        --enable-local-transport \
        --enable-malloc0returnsnull

    make -j4 && make install
}

build_script_xkbcommon() {
    meson setup build \
        --prefix ${MY_PREFIX} \
        --buildtype release \
        --cross-file ../aarch64_xkbcommon.txt \
        -D enable-x11=true \
        -D enable-wayland=false \
        -D enable-docs=false \
        -D enable-xkbregistry=false \
        -D xkb-config-root=${MY_PREFIX}/lib/pkgconfig

    ninja -C build
    ninja -C build install
}

build_script_selinux() {
    export CC=${MY_HOST}-gcc
    export CXX=${MY_HOST}-g++
    export PREFIX=${MY_PREFIX}
    export SHLIBDIR=${MY_PREFIX}/lib
    make -j4 && make install
}

build_script_freetype() {
    ./configure \
        --prefix=${MY_PREFIX} \
        --host=${MY_HOST} \
        --with-zlib=no \
        --with-png=no \
        --enable-freetype-config

    make -j4 && make install
}

build_script_xml2() {
    ./configure \
        --prefix=${MY_PREFIX} \
        --host=${MY_HOST} \
        --with-zlib=no \
        --without-python

    make -j4 && make install
}

build_script_zlib() {
    ./configure \
        --prefix=${MY_PREFIX} \
        --shared \
        --static

    make -j4 && make install
}

build_script_glib() {
    meson setup build \
        --prefix ${MY_PREFIX} \
        --buildtype release \
        --cross-file ../aarch64_glib.txt \
        -D libmount=false

    ninja -C build
    ninja -C build install
}

build_script_mesa() {
    export CFLAGS="-I${MY_PREFIX}/include/libdrm -I${MY_PREFIX}/include/libdrm/nouveau $CFLAGS"
    meson setup build \
        --prefix ${MY_PREFIX} \
        --buildtype release \
        --cross-file ../aarch64_mesa.txt \
        -D gallium-drivers=nouveau,freedreno \
        -D platforms=x11

    ninja -C build
    ninja -C build install
}

build_script_icu() {
    mkdir $(pwd)/build
    cd $(pwd)/build
    ../runConfigureICU Linux/gcc
    make
    cd ..

    ./configure \
        --prefix=${MY_PREFIX} \
        --host=${MY_HOST} \
        --with-cross-build=$(pwd)/build

    make -j4 && make install
}

build_script_nodejs() {
    #linux host env
    export CC_host=gcc
    export CXX_host=g++

    #cross-compile env
    export CC=${MY_HOST}-gcc
    export CXX=${MY_HOST}-g++
    export AR=${MY_HOST}-ar
    export RANLIB=${MY_HOST}-ranlib

    #execute configure
    ./configure \
        --prefix=${MY_PREFIX} \
        --dest-cpu=arm64 \
        --dest-os=linux \
        --cross-compiling \
        --without-snapshot \
        --openssl-no-asm \
        --shared

    make -j4 && make install
}

build_openssl() {
    rm -rf openssl-1.1.1q
    tar -xvf openssl-1.1.1q.tar.gz
    cd openssl-1.1.1q
    build_script_openssl
    cd ..
}

build_xtrans() {
    rm -rf xtrans-1.4.0
    tar -xvf xtrans-1.4.0.tar.gz
    cd xtrans-1.4.0
    build_script_xcb_common
    cd ..
}

build_xcb_proto() {
    rm -rf xcb-proto-1.13
    tar -xvf xcb-proto-1.13.tar.gz
    cd xcb-proto-1.13
    build_script_xcb_common
    cd ..
}

build_xorgproto() {
    rm -rf xorgproto-2020.1
    tar -xvf xorgproto-2020.1.tar.gz
    cd xorgproto-2020.1
    build_script_xcb_common
    cd ..
}

build_Xau() {
    rm -rf libXau-1.0.9
    tar -xvf libXau-1.0.9.tar.gz
    cd libXau-1.0.9
    build_script_xcb_common
    cd ..
}

build_xcb() {
    rm -rf libxcb-1.13
    tar -xvf libxcb-1.13.tar.gz
    cd libxcb-1.13
    build_script_xcb_common
    cd ..
}

build_pthread() {
    rm -rf libpthread-stubs-0.4
    tar -xvf libpthread-stubs-0.4.tar.gz
    cd libpthread-stubs-0.4
    build_script_xcb_common
    cd ..
}

build_xcb_util() {
    rm -rf xcb-util-0.3.9
    tar -xvf xcb-util-0.3.9.tar.gz
    cd xcb-util-0.3.9
    build_script_xcb_common
    cd ..
}

build_xcb_util_image() {
    rm -rf xcb-util-image-0.3.9
    tar -xvf xcb-util-image-0.3.9.tar.gz
    cd xcb-util-image-0.3.9
    build_script_xcb_common
    cd ..
}

build_xcb_util_keysyms() {
    rm -rf xcb-util-keysyms-0.3.9
    tar -xvf xcb-util-keysyms-0.3.9.tar.gz
    cd xcb-util-keysyms-0.3.9
    build_script_xcb_common
    cd ..
}

build_xcb_util_renderutil() {
    rm -rf xcb-util-renderutil-0.3.9
    tar -xvf xcb-util-renderutil-0.3.9.tar.gz
    cd xcb-util-renderutil-0.3.9
    build_script_xcb_common
    cd ..
}

build_xcb_util_wm() {
    rm -rf xcb-util-wm-0.3.9
    tar -xvf xcb-util-wm-0.3.9.tar.gz
    cd xcb-util-wm-0.3.9
    build_script_xcb_common
    cd ..
}

build_util_macros() {
    rm -rf util-macros-1.19.3
    tar -xvf util-macros-1.19.3.tar.gz
    cd util-macros-1.19.3
    build_script_xcb_common
    cd ..
}

build_xrender() {
    rm -rf libXrender-0.9.10
    tar -xvf libXrender-0.9.10.tar.gz
    cd libXrender-0.9.10
    build_script_xcb_common
    cd ..
}

build_xext() {
    rm -rf libXext-1.3.4
    tar -xvf libXext-1.3.4.tar.gz
    cd libXext-1.3.4
    build_script_xcb_common
    cd ..
}

build_drm() {
    rm -rf libdrm-2.4.100
    tar -xvf libdrm-2.4.100.tar.gz
    cd libdrm-2.4.100
    build_script_xcb_common
    cd ..
}

build_xrandr() {
    rm -rf libXrandr-1.5.2
    tar -xvf libXrandr-1.5.2.tar.gz
    cd libXrandr-1.5.2
    build_script_xcb_common
    cd ..
}

build_xfixes() {
    rm -rf libXfixes-5.0.3
    tar -xvf libXfixes-5.0.3.tar.gz
    cd libXfixes-5.0.3
    build_script_xcb_common
    cd ..
}

build_xcomposite() {
    rm -rf libXcomposite-0.4.5
    tar -xvf libXcomposite-0.4.5.tar.gz
    cd libXcomposite-0.4.5
    build_script_xcb_common
    cd ..
}

build_xcursor() {
    rm -rf libXcursor-1.2.0
    tar -xvf libXcursor-1.2.0.tar.gz
    cd libXcursor-1.2.0
    build_script_xcb_common
    cd ..
}

build_xi() {
    rm -rf libXi-1.7.10
    tar -xvf libXi-1.7.10.tar.gz
    cd libXi-1.7.10
    build_script_xcb_common
    cd ..
}

build_xscrnsaver() {
    rm -rf libXScrnSaver-1.2.3
    tar -xvf libXScrnSaver-1.2.3.tar.gz
    cd libXScrnSaver-1.2.3
    build_script_xcb_common
    cd ..
}

build_xtst() {
    rm -rf libXtst-1.2.3
    tar -xvf libXtst-1.2.3.tar.gz
    cd libXtst-1.2.3
    build_script_xcb_common
    cd ..
}

build_xshmfence() {
    rm -rf libxshmfence-1.3
    tar -xvf libxshmfence-1.3.tar.gz
    cd libxshmfence-1.3
    build_script_xcb_common
    cd ..
}

build_xxf86vm() {
    rm -rf libXxf86vm-1.1.4
    tar -xvf libXxf86vm-1.1.4.tar.gz
    cd libXxf86vm-1.1.4
    build_script_xcb_common
    cd ..
}

build_xkeyboard() {
    rm -rf xkeyboard-config-2.30
    tar -xvf xkeyboard-config-2.30.tar.gz
    cd xkeyboard-config-2.30
    build_script_xcb_common
    cd ..
}

build_xkbcommon() {
    rm -rf libxkbcommon-1.4.0
    tar -xvf libxkbcommon-1.4.0.tar.xz
    cd libxkbcommon-1.4.0
    build_script_xkbcommon
    cd ..
}

build_ice() {
    rm -rf libICE-1.0.10
    tar -xvf libICE-1.0.10.tar.gz
    cd libICE-1.0.10
    build_script_xcb_common
    cd ..
}

build_sm() {
    rm -rf libSM-1.2.3
    tar -xvf libSM-1.2.3.tar.gz
    cd libSM-1.2.3
    build_script_xcb_common
    cd ..
}

build_x11() {
    rm -rf libX11-1.7.5
    tar -xvf libX11-1.7.5.tar.gz
    cd libX11-1.7.5
    build_script_x11
    cd ..
}

# glib
build_pcre() {
    rm -rf pcre-8.45
    tar -xvf pcre-8.45.tar.gz
    cd pcre-8.45
    build_script_xcb_common
    cd ..
}

build_zlib() {
    rm -rf zlib-1.2.11
    tar -xvf zlib-1.2.11.tar.gz
    cd zlib-1.2.11
    build_script_zlib
    cd ..
}

build_ffi() {
    rm -rf libffi-3.3
    tar -xvf libffi-3.3.tar.gz
    cd libffi-3.3
    build_script_xcb_common
    cd ..
}

build_glib() {
    rm -rf glib-2.61.3
    tar -xvf glib-2.61.3.tar.xz
    cd glib-2.61.3
    build_script_glib
    cd ..
}

# webengine
build_xkbfile() {
    rm -rf libxkbfile-1.1.0
    tar -xvf libxkbfile-1.1.0.tar.gz
    cd libxkbfile-1.1.0
    build_script_xcb_common
    cd ..
}

build_xdamage() {
    rm -rf libXdamage-1.1.5
    tar -xvf libXdamage-1.1.5.tar.gz
    cd libXdamage-1.1.5
    build_script_xcb_common
    cd ..
}

build_expat() {
    rm -rf expat-2.2.9
    tar -xvf expat-2.2.9.tar.gz
    cd expat-2.2.9
    build_script_xcb_common
    cd ..
}

build_sepol() {
    rm -rf libsepol-3.0
    tar -xvf libsepol-3.0.tar.gz
    cd libsepol-3.0
    build_script_selinux
    cd ..
}

build_selinux() {
    rm -rf libselinux-3.0
    tar -xvf libselinux-3.0.tar.gz
    cd libselinux-3.0
    build_script_selinux
    cd ..
}

build_dbus() {
    rm -rf dbus-1.13.6
    tar -xvf dbus-1.13.6.tar.gz
    cd dbus-1.13.6
    build_script_xcb_common
    cd ..
}

build_freetype() {
    rm -rf freetype-2.10.1
    tar -xvf freetype-2.10.1.tar.gz
    cd freetype-2.10.1
    build_script_freetype
    cd ..
}

build_xml2() {
    rm -rf libxml2-v2.9.9
    tar -xvf libxml2-v2.9.9.tar.gz
    cd libxml2-v2.9.9
    ./autogen.sh
    build_script_xml2
    cd ..
}

build_uuid() {
    rm -rf libuuid-1.0.3
    tar -xvf libuuid-1.0.3.tar.gz
    cd libuuid-1.0.3
    build_script_xcb_common
    cd ..
}

build_fontconfig() {
    rm -rf fontconfig-2.13.92
    tar -xvf fontconfig-2.13.92.tar.gz
    cd fontconfig-2.13.92
    build_script_xcb_common
    cd ..
}

build_sqlite3() {
    rm -rf sqlite-version-3.30.1
    tar -xvf version-3.30.1.tar.gz
    cd sqlite-version-3.30.1
    build_script_xcb_common
    cd ..
}

build_mesa() {
    rm -rf mesa-mesa-19.0.0
    tar -xvf mesa-mesa-19.0.0.tar.gz
    cd mesa-mesa-19.0.0
    build_script_mesa
    cd ..
}

build_icu() {
    rm -rf icu
    tar -xvf icu4c-65_1-src.tgz
    cd icu/source
    build_script_icu
    cd ../..
}

build_nodejs() {
    rm -rf node-v10.24.1
    tar -xvf node-v10.24.1.tar.gz
    cd node-v10.24.1
    build_script_nodejs
    cd ..
}

# openssl
build_openssl

# glib
build_pcre
build_zlib
build_ffi
build_sepol
build_selinux
build_glib

# x11
build_xtrans
build_xcb_proto
build_xorgproto
build_Xau
build_xcb
build_pthread
build_xcb_util
build_xcb_util_image
build_xcb_util_keysyms
build_xcb_util_renderutil
build_xcb_util_wm
build_util_macros
build_xkeyboard
build_drm
build_xshmfence
build_xkbcommon
build_ice
build_sm
build_x11

# webengine
build_xrender
build_xext
build_xrandr
build_xfixes
build_xcomposite
build_xcursor
build_xi
build_xscrnsaver
build_xtst
build_xxf86vm
build_xkbfile
build_xdamage
build_expat
build_dbus
build_freetype
build_xml2
build_uuid
build_fontconfig
build_sqlite3
build_mesa
build_icu
build_nodejs

2.5.3. nss交叉编译

webengine 模块需要用到 nssnss 交叉编译比较麻烦,具体步骤参考linux交叉编译nss3,nspr-爱代码爱编程2

以下列出需要用到的命令,下面脚本不能直接执行,以参考链接为准。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
#!/bin/sh
MY_PREFIX=/usr/local
MY_PREFIX_CROSS=/aarch64

# build_init() {
#     rm -rf nss-3.50
#     tar -xvf nss-3.50-with-nspr-4.25.tar.gz
#     cd nss-3.50
#     patch -Np1 -i ../nss-3.50-standalone-1.patch
#     cp -rf nspr nspr_local
#     cp -rf nss nss_local
# }

build_script_nspr_local() {
    cd nspr_local

    sed -i '/^RELEASE/s|^|#|' pr/src/misc/Makefile.in
    sed -i 's|$(LIBRARY) ||' config/rules.mk

    ./configure \
        --with-pthreads \
        --enable-64bit \
        --with-mozilla

    make -j1 && make install
}

build_script_nspr() {
    cd nspr

    sed -i '/^RELEASE/s|^|#|' pr/src/misc/Makefile.in
    sed -i 's|$(LIBRARY) ||' config/rules.mk

    ./configure \
        --prefix=${MY_PREFIX_CROSS} \
        --host=aarch64-linux-gnu \
        --with-pthreads \
        --with-mozilla \
        --enable-64bit

    make -j1 && make install
    # cp ./nspr_local/config/nsinstall ./nspr/config/
}

build_script_nss_local() {
    cd nss_local

    make -j1 \
        BUILD_OPT=1 \
        NSPR_INCLUDE_DIR=${MY_PREFIX}/include/nspr \
        NSPR_LIB_DIR=${MY_PREFIX}/lib \
        USE_STATIC_RTL=1 \
        USE_SYSTEM_ZLIB=1 \
        ZLIB_LIBS=-lz \
        NSS_ENABLE_WERROR=0 \
        $([ -f ${MY_PREFIX}/include/sqlite3.h ] && echo NSS_USE_SYSTEM_SQLITE=1) \
        $([ $(uname -m) = x86_64 ] && echo USE_64=1)
}

build_script_nss() {
    cd nss

    export CC=/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-gcc
    export CCC=/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin/aarch64-linux-gnu-g++
    export C_INCLUDE_PATH=${MY_PREFIX_CROSS}/include:$C_INCLUDE_PATH
    export LD_LIBRARY_PATH=${MY_PREFIX_CROSS}/lib:$LD_LIBRARY_PATH

    make -j1 \
        BUILD_OPT=1 \
        NSPR_INCLUDE_DIR=${MY_PREFIX_CROSS}/include/nspr \
        NSPR_LIB_DIR=${MY_PREFIX_CROSS}/lib \
        USE_STATIC_RTL=1 \
        USE_SYSTEM_ZLIB=1 \
        ZLIB_LIBS=-lz \
        NSS_ENABLE_WERROR=0 \
        $([ -f ${MY_PREFIX_CROSS}/include/sqlite3.h ] && echo NSS_USE_SYSTEM_SQLITE=1) \
        USE_64=1 \
        CROSS_COMPILE=1 \
        PREFIX=${MY_PREFIX_CROSS} \
        OS_TEST=aarch64

    cd ..
    # cp ./nss_local/coreconf/nsinstall/Linux3.10_x86_64_cc_glibc_PTH_64_OPT.OBJ/nsinstall ./nss/coreconf/nsinstall/Linux3.10_aarch64_glibc_PTH_64_OPT.OBJ/
}

install_nss() {
    cd ./dist/Linux3.10_aarch64_glibc_PTH_64_OPT.OBJ

    install -v -m755 lib/*.so ${MY_PREFIX_CROSS}/lib
    install -v -m644 lib/{*.chk,libcrmf.a} ${MY_PREFIX_CROSS}/lib
    install -v -m755 -d ${MY_PREFIX_CROSS}/include/nss
    cp -v -RL ../{public,private}/nss/* ${MY_PREFIX_CROSS}/include/nss
    install -v -m755 bin/{certutil,nss-config,pk12util} ${MY_PREFIX_CROSS}/bin
    install -v -m644 lib/pkgconfig/nss.pc ${MY_PREFIX_CROSS}/lib/pkgconfig
    
    cd ..
}

# 编译 nss
# build_init
build_script_nspr_local
build_script_nspr

build_script_nss_local
build_script_nss

install_nss

2.5.4. nodejs下载

nodejs 不用交叉编译,下载创建链接即可。

1
2
3
4
5
6
7
# 下载 nodejs
wget -c https://registry.npmmirror.com/-/binary/node/v10.24.1/node-v10.24.1-linux-x64.tar.gz
tar -xvf node-v10.24.1-linux-x64.tar.gz
mv node-v10.24.1-linux-x64 /usr/local/nodejs
# 建立node npm软链接
ln -s /usr/local/nodejs/bin/node /usr/local/bin
ln -s /usr/local/nodejs/bin/npm /usr/local/bin

2.5.5. 检查编译3

文件都放在 /cross/dependence

以下脚本是检查是否能被检索到。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
#!/bin/bash
PRE_PATH=/aarch64

export PKG_CONFIG_PATH=${PRE_PATH}/lib/pkgconfig:${PRE_PATH}/share/pkgconfig

x11string="xrender,xcb-render,xcb-renderutil,xcb-shape,xcb-randr,xcb-xfixes,xcb-sync,xcb-shm,xcb-icccm,xcb-keysyms,xcb-image,xkbcommon,xkbcommon-x11,fontconfig,freetype2,xext,x11,xcb,x11-xcb,sm,ice,glib-2.0,xcb-xinerama"
x11array=(${x11string//,/ })

webstring="nss,libdrm,xcomposite,xcursor,xi,xrandr,xscrnsaver,xtst,xkbfile,expat,xdamage"
webarray=(${webstring//,/ })

allCount=0
successCount=0
failedStr=""

echo "X11依赖:"
for var in ${x11array[@]}; do
    let allCount++
    modversion="$(pkg-config --modversion --silence-errors $var)"

    if [[ -n $modversion ]]; then
        let successCount++
        echo $var "库版本号" $modversion
    else
        failedStr=$failedStr$var,
        echo $var "未找到库!!!"
    fi
done

echo
echo "WebEngine依赖:"
for var in ${webarray[@]}; do
    let allCount++
    modversion="$(pkg-config --modversion --silence-errors $var)"

    if [[ -n $modversion ]]; then
        let successCount++
        echo $var "库版本号" $modversion
    else
        failedStr=$failedStr$var,
        echo $var "未找到库!!!"
    fi
done

echo
echo "成功 / 总数:"$successCount/$allCount
if [ $allCount -ne $successCount ]; then
    echo "未找到的库 :"$failedStr
fi

运行上述脚本全部找到应该就没问题。

3. 编译Qt

下载地址:https://download.qt.io/archive/qt/5.15/5.15.2/single/

首先解压,以后所有操作都在 /cross/qt-everywhere-src-5.15.2 中操作

1
2
tar -xvf qt-everywhere-src-5.15.2.tar.xz
cd qt-everywhere-src-5.15.2

3.1. 环境配置

因为要配置 sysroot,所有查找路径都会加上 ${sysroot} 前缀,所以需要把上述所有依赖安装路径 aarch64 文件夹拷贝到 sysroot-aarch64 目录下。

将原来 aarch64 改名,不然 qt 后续编译 webengine 本地链接 nss 会找到这里面。

1
2
3
4
5
6
# 移动和改名
cp -rf /aarch64 /sysroot-aarch64/
mv /aarch64 /aarch641

# 或者直接移动
mv /aarch64/ /sysroot-aarch64/

不知道为什么 webengine 模块不能识别编译脚本中的 export,所以需要在 /etc/profile 设置

1
2
3
4
5
6
7
8
9
10
11
12
vim /etc/profile

# webengine
MY_SYSROOT=/sysroot-aarch64
MY_PREFIX=${MY_SYSROOT}/aarch64
export PKG_CONFIG_PATH=${MY_PREFIX}/lib/pkgconfig:${MY_PREFIX}/share/pkgconfig
export CPLUS_INCLUDE_PATH=$CPLUS_INCLUDE_PATH:${MY_PREFIX}/include
export CPLUS_INCLUDE_PATH=$CPLUS_INCLUDE_PATH:${MY_PREFIX}/include/nss
export CPLUS_INCLUDE_PATH=$CPLUS_INCLUDE_PATH:${MY_PREFIX}/include/nspr
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:${MY_PREFIX}/lib

source /etc/profile

3.2. 添加交叉编译平台

所有默认的交叉编译平台配置文件在 /qt-everywhere-src-5.15.2/qtbase/mkspecs,为了不影响文件,可以复制 linux-aarch64-gnu-g++aarch64-linux-gnu-g++ 作为我们的配置文件。修改 qmake.conf 文件如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
#
# qmake configuration for building with aarch64-linux-gnu-g++
#

MAKEFILE_GENERATOR      = UNIX
CONFIG                 += incremental
QMAKE_INCREMENTAL_STYLE = sublib

include(../common/linux.conf)
include(../common/gcc-base-unix.conf)
include(../common/g++-unix.conf)

QMAKE_INCDIR_POST += \ 
    $$[QT_SYSROOT]/usr/include \
    $$[QT_SYSROOT]/aarch64/include

QMAKE_RPATHLINKDIR_POST += \ 
    $$[QT_SYSROOT]/usr/lib \
    $$[QT_SYSROOT]/aarch64/lib \
    $$[QT_SYSROOT]/aarch64/lib64

# modifications to g++.conf
QMAKE_CC                = aarch64-linux-gnu-gcc
QMAKE_CXX               = aarch64-linux-gnu-g++
QMAKE_LINK              = aarch64-linux-gnu-g++
QMAKE_LINK_SHLIB        = aarch64-linux-gnu-g++

# modifications to linux.conf
QMAKE_AR                = aarch64-linux-gnu-ar cqs
QMAKE_OBJCOPY           = aarch64-linux-gnu-objcopy
QMAKE_NM                = aarch64-linux-gnu-nm -P
QMAKE_STRIP             = aarch64-linux-gnu-strip
load(qt_config)

3.3. 编译脚本

为了不污染源代码,所以脚本 aarch64_qt.sh 创建 build 文件夹进行编译。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
#!/bin/sh
mkdir build
cd build

MY_SYSROOT=/sysroot-aarch64
MY_PREFIX=${MY_SYSROOT}/aarch64
MY_XPLATFORM=aarch64-linux-gnu-g++

export PKG_CONFIG_LIBDIR=${MY_PREFIX}/lib/pkgconfig:${MY_PREFIX}/share/pkgconfig
export PKG_CONFIG_PATH=${MY_PREFIX}/lib/pkgconfig:${MY_PREFIX}/share/pkgconfig

../configure \
    -prefix /opt/qt5.15.2 \
    -confirm-license \
    -opensource \
    -release \
    -sysroot ${MY_SYSROOT} \
    -pkg-config \
    -xplatform ${MY_XPLATFORM} \
    -I${MY_PREFIX}/include \
    -L${MY_PREFIX}/lib \
    -make libs \
    -nomake examples \
    -nomake tools \
    -nomake tests \
    -xcb \
    -dbus \
    -fontconfig

cd ..

执行命令 ./aarch64_qt.sh,看到以下情况即是包含 OpenSSL X11 QWebEngine,就可以开始编译。

1
2
3
4
5
cd build
# 编译
gmake -j4
# 安装,路径是 /sysroot-aarch64/opt/qt5.15.2
gmake install

3.4. 问题

出现找不到模块,请仔细查看 config.cacheconfig.log 排查。

以下是编译 qt5.15.2 源码时源码出现的问题

3.4.1. chromium/third_party/libjpeg_turbo4

1
2
3
4
5
6
7
8
9
10
../../../../../qtwebengine/src/3rdparty/chromium/third_party/libjpeg_turbo/simd/arm/common/jidctint-neon.c: In function ‘jsimd_idct_islow_neon’:
../../../../../qtwebengine/src/3rdparty/chromium/third_party/libjpeg_turbo/simd/arm/common/jidctint-neon.c:217:30: error: incompatible types when initializing type ‘int64_t {aka long int}’ using type ‘int64x1_t’
   int64_t bitmap_rows_4567 = vreinterpret_s64_s16(bitmap);
                              ^
../../../../../qtwebengine/src/3rdparty/chromium/third_party/libjpeg_turbo/simd/arm/common/jidctint-neon.c:223:30: error: incompatible types when initializing type ‘int64_t {aka long int}’ using type ‘int64x1_t’
     int64_t left_ac_bitmap = vreinterpret_s64_s16(bitmap);
                              ^
../../../../../qtwebengine/src/3rdparty/chromium/third_party/libjpeg_turbo/simd/arm/common/jidctint-neon.c:227:30: warning: missing braces around initializer [-Wmissing-braces]
       int16x4x4_t quadrant = { dcval, dcval, dcval, dcval };
                              ^

根据提示显示类型不兼容,进行修改 jidctfst-neon.c jidctint-neon.c jidctred-neon.c 这三个文件

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
// jidctfst-neon.c
// 87
int64_t left_ac_bitmap = vreinterpret_s64_s16(vget_low_s16(bitmap));
int64_t right_ac_bitmap = vreinterpret_s64_s16(vget_high_s16(bitmap));
// 改为
int64_t left_ac_bitmap = vget_lane_s64(vreinterpret_s64_s16(vget_low_s16(bitmap)), 0);
int64_t right_ac_bitmap = vget_lane_s64(vreinterpret_s64_s16(vget_high_s16(bitmap)), 0);
// 407
  uint8x16_t cols_01 = vreinterpretq_u8_s8(
                            vaddq_s8(cols_01_s8, vdupq_n_u8(CENTERJSAMPLE)));
  uint8x16_t cols_45 = vreinterpretq_u8_s8(
                            vaddq_s8(cols_45_s8, vdupq_n_u8(CENTERJSAMPLE)));
  uint8x16_t cols_23 = vreinterpretq_u8_s8(
                            vaddq_s8(cols_23_s8, vdupq_n_u8(CENTERJSAMPLE)));
  uint8x16_t cols_67 = vreinterpretq_u8_s8(
                            vaddq_s8(cols_67_s8, vdupq_n_u8(CENTERJSAMPLE)));
// 改为
  uint8x16_t cols_01 = vreinterpretq_u8_s8(
                            vaddq_s8(cols_01_s8, (int8x16_t)vdupq_n_u8(CENTERJSAMPLE)));
  uint8x16_t cols_45 = vreinterpretq_u8_s8(
                            vaddq_s8(cols_45_s8, (int8x16_t)vdupq_n_u8(CENTERJSAMPLE)));
  uint8x16_t cols_23 = vreinterpretq_u8_s8(
                            vaddq_s8(cols_23_s8, (int8x16_t)vdupq_n_u8(CENTERJSAMPLE)));
  uint8x16_t cols_67 = vreinterpretq_u8_s8(
                            vaddq_s8(cols_67_s8, (int8x16_t)vdupq_n_u8(CENTERJSAMPLE)));

// jidctint-neon.c
// 217 223 269 273 280
int64_t bitmap_rows_4567 = vreinterpret_s64_s16(bitmap);
int64_t left_ac_bitmap = vreinterpret_s64_s16(bitmap);
bitmap_rows_4567 = vreinterpret_s64_s16(bitmap);
int64_t right_ac_bitmap = vreinterpret_s64_s16(bitmap);
right_ac_dc_bitmap = vreinterpret_s64_s16(bitmap);
// 改为
int64_t bitmap_rows_4567 = vget_lane_s64(vreinterpret_s64_s16(bitmap),0);
int64_t left_ac_bitmap = vget_lane_s64(vreinterpret_s64_s16(bitmap),0);
bitmap_rows_4567 = vget_lane_s64(vreinterpret_s64_s16(bitmap),0);
int64_t right_ac_bitmap = vget_lane_s64(vreinterpret_s64_s16(bitmap),0);
right_ac_dc_bitmap = vget_lane_s64(vreinterpret_s64_s16(bitmap),0);
// 350 这个是交叉编译低版本没有,64位直接使用32位同样效果
const int16x4x3_t consts = vld1_s16_x3(jsimd_idct_islow_neon_consts);

// jidctred-neon.c
// 220
int64_t left_ac_bitmap = vreinterpret_s64_s16(vget_low_s16(bitmap));
int64_t right_ac_bitmap = vreinterpret_s64_s16(vget_high_s16(bitmap));
// 改为
int64_t left_ac_bitmap = vget_lane_s64(vreinterpret_s64_s16(vget_low_s16(bitmap)),0);
int64_t right_ac_bitmap = vget_lane_s64(vreinterpret_s64_s16(vget_low_s16(bitmap)),0);
// 225 这个是交叉编译低版本没有,64位直接使用32位同样效果
const int16x4x3_t consts = vld1_s16_x3(jsimd_idct_4x4_neon_consts);

3.4.2. chromium/v85

1
2
3
4
5
6
7
8
9
10
11
../../../../../qtwebengine/src/3rdparty/chromium/v8/src/codegen/arm64/macro-assembler-arm64.h:1423:25: error: use of deleted function ‘v8::internal::TurboAssembler::TurboAssembler(v8::internal::Isolate*, v8::internal::CodeObjectRequired, std::unique_ptr<v8::internal::AssemblerBuffer>)’
../../../../../qtwebengine/src/3rdparty/chromium/v8/src/codegen/arm64/macro-assembler-arm64.h:150:29: note: ‘v8::internal::TurboAssembler::TurboAssembler(v8::internal::Isolate*, v8::internal::CodeObjectRequired, std::unique_ptr<v8::internal::AssemblerBuffer>)’ is implicitly deleted because the default definition would be ill-formed:
   using TurboAssemblerBase::TurboAssemblerBase;
                             ^
../../../../../qtwebengine/src/3rdparty/chromium/v8/src/codegen/arm64/macro-assembler-arm64.h:150:29: error: no matching function for call to ‘v8::internal::CPURegList::CPURegList()’
In file included from ../../../../../qtwebengine/src/3rdparty/chromium/v8/src/codegen/register-arch.h:16:0,
                 from ../../../../../qtwebengine/src/3rdparty/chromium/v8/src/deoptimizer/deoptimizer.h:13,
                 from ../../../../../qtwebengine/src/3rdparty/chromium/v8/../../../../../qtwebengine/src/3rdparty/chromium/v8/src/deoptimizer/deoptimizer.cc:5,
                 from gen/v8/v8_base_without_compiler_jumbo_13.cc:6:
../../../../../qtwebengine/src/3rdparty/chromium/v8/src/codegen/arm64/register-arm64.h:539:3: note: candidate: v8::internal::CPURegList::CPURegList(v8::internal::CPURegister::RegisterType, int, int, int)
   CPURegList(CPURegister::RegisterType type, int size, int first_reg,

这是头文件中缺少 CPURegList 默认构造函数,在register-arm64.h533 行添加以下代码即可

1
2
3
4
// 533
  CPURegList() {
    DCHECK(is_valid());
  }

4. 验证

经过上述步骤就能获得 arm64 版本的 qt5.15.2,接下来是验证是否可以将程序编译成 arm64 版本,主要验证 webengine 模块功能。

下载安装 qt-opensource-linux-x64-5.14.2.run 最后一个离线安装版本:https://download.qt.io/archive/qt/5.14/5.14.2/。

添加交叉编译版本 qmake 路径,不然不能加载

1
2
3
4
5
6
vim /etc/profile

# qmake-aarch64
export PATH=$PATH:/sysroot-aarch64/opt/qt5.15.2/bin

source /etc/profile

4.1. 添加构建环境

在工具——选项——Kits——Qt Versions中点击添加,选择交叉编译生成的 qmake,配置了环境变量交叉编译器一般会自动加入。

然后在构建套件中添加一个交叉编译 arm64 版本,参数如下:

使用 simplebrowser.pro 示例进行测试。可以看到最终编译结果是 arm64 版本。

5. 总结

5.1. /etc/profile

最后 /etc/profile 文件如下:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
# gcc-aarch64
export PATH=$PATH:/cross/gcc-linaro-5.4.1-2017.05-x86_64_aarch64-linux-gnu/bin
# gcc,放前面覆盖原始 gcc 路径
export PATH=/usr/local/gcc/bin:$PATH
export LD_LIBRARY_PATH=/usr/local/gcc/lib64:$LD_LIBRARY_PATH

# webengine
MY_SYSROOT=/sysroot-aarch64
MY_PREFIX=${MY_SYSROOT}/aarch64
export PKG_CONFIG_PATH=${MY_PREFIX}/lib/pkgconfig:${MY_PREFIX}/share/pkgconfig
export CPLUS_INCLUDE_PATH=$CPLUS_INCLUDE_PATH:${MY_PREFIX}/include
export CPLUS_INCLUDE_PATH=$CPLUS_INCLUDE_PATH:${MY_PREFIX}/include/nss
export CPLUS_INCLUDE_PATH=$CPLUS_INCLUDE_PATH:${MY_PREFIX}/include/nspr
export LD_LIBRARY_PATH=$LD_LIBRARY_PATH:${MY_PREFIX}/lib

# qmake-aarch64
export PATH=$PATH:${MY_SYSROOT}/opt/qt5.15.2/bin

参考

本文由作者按照 CC BY 4.0 进行授权