ubuntu16.04 下编译和运行 c++ proto-quic quic_server quic_client

下载proto-quic源码

1
2
3
4
5
$sudo su
# 将这次编译所需的东西统一放在这个目录下
$mkdir quic_stuff
$cd quic_stuff
$git clone https://github.com/google/proto-quic.git

我测试时proto-quic的版本:git commit id: 9f1ab92724ce2647585e62b0e8155ee7368697ce

安装依赖

如果是第一次安装,需要先安装依赖

1
2
3
4
5
6
7
8
9
10
11
12
13
14
#cd 进入 quic_stuff/proto-quic
$export PROTO_QUIC_ROOT=`pwd`/src
$export PATH=$PATH:`pwd`/depot_tools
$./src/build/install-build-deps.sh

# -----问题1.
# 期间会弹出一个红底界面的关于安装Configuring ttf-mscorefonts-installer的LICENSE确认,
# 先按Tab键切换到Ok按键,按回车,再方向键切换到Yes按键回车确认即可。

# -----问题2. 如果出现如下错误:
# ERROR: The installation of the Chrome OS default fonts failed.
#
# 说明安装Chrome OS的字体失败了,解决方法是不安装Chrome OS的字体
$./src/build/install-build-deps.sh --no-chromeos-fonts

用gn生成ninja编译所需的文件

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
#cd 进入 quic_stuff/proto-quic/src
$gn gen out/Default

# -----问题1. 如果出现如下错误:
# .gclient file in parent directory /root/quic_stuff/proto-quic might not be the file you want to use
# ERROR at //build/config/sysroot.gni:67:5: Assertion failed.
# assert(
# ^-----
# Missing sysroot (//build/linux/debian_jessie_amd64-sysroot). To fix, run: build/linux/sysroot_scripts/install-sysroot.py --arch=amd64
# See //build/config/sysroot.gni:68:9:
# exec_script("//build/dir_exists.py",
# ^-----------------------------------
# This is where it was set.
# See //build/toolchain/linux/BUILD.gn:5:1: whence it was imported.
# import("//build/config/sysroot.gni")
# ^----------------------------------
# See //BUILD.gn:11:1: which caused the file to be included.
# group("root") {
#
# 说明需要安装sysroot,错误提示中给出了安装方法:
$build/linux/sysroot_scripts/install-sysroot.py
#
# 执行如果出现如下错误:
# Installing Debian Jessie amd64 root image: /root/quic_stuff/proto-quic/src/build/linux/debian_jessie_amd64-sysroot
# Downloading https://commondatastorage.googleapis.com/chrome-linux-sysroot/toolchain/e6ac45fd042859d2240e5d432c521df01ad5b7bf/debian_jessie_amd64_sysroot.tar.xz
# /root/quic_stuff/proto-quic/src/build/linux/debian_jessie_amd64-sysroot/debian_jessie_amd64_sysroot.tar.xz
# Traceback (most recent call last):
# File "build/linux/sysroot_scripts/install-sysroot.py", line 231, in <module>
# sys.exit(main(sys.argv[1:]))
# File "build/linux/sysroot_scripts/install-sysroot.py", line 154, in main
# InstallDefaultSysrootForArch(options.arch)
# File "build/linux/sysroot_scripts/install-sysroot.py", line 168, in InstallDefaultSysrootForArch
# InstallSysroot('Jessie', target_arch)
# File "build/linux/sysroot_scripts/install-sysroot.py", line 218, in InstallSysroot
# sha1sum = GetSha1(tarball)
# File "build/linux/sysroot_scripts/install-sysroot.py", line 51, in GetSha1
# with open(filename, 'rb') as f:
# IOError: [Errno 2] No such file or directory: u'/root/quic_stuff/proto-quic/src/build/linux/debian_jessie_amd64-sysroot/debian_jessie_amd64_sysroot.tar.xz'
#
# 这是由于我的环境网络没有翻墙,下载失败了。
# 解决方法是在允许翻墙的环境将文件下载后,并拷贝至相应位置
# 文件下载地址:
# https://commondatastorage.googleapis.com/chrome-linux-sysroot/toolchain/e6ac45fd042859d2240e5d432c521df01ad5b7bf/debian_jessie_amd64_sysroot.tar.xz
# 需要拷贝至:
# /root/quic_stuff/proto-quic/src/build/linux/debian_jessie_amd64-sysroot/debian_jessie_amd64_sysroot.tar.xz
#
# 然后还需要修改代码,让它跳过下载这一步:
# 200 #if os.path.isdir(sysroot):
# 201 # shutil.rmtree(sysroot)
# 202 #os.mkdir(sysroot)
# 203 tarball = os.path.join(sysroot, tarball_filename)
# 204 print 'Downloading %s' % url
# 205 sys.stdout.flush()
# 206 sys.stderr.flush()
# 207 #for _ in range(3):
# 208 # try:
# 209 # response = urllib2.urlopen(url)
# 210 # with open(tarball, "wb") as f:
# 211 # f.write(response.read())
# 212 # break
# 213 # except:
# 214 # pass
# 215 #else:
# 216 # raise Error('Failed to download %s' % url)
#
# 再次执行安装sysroot
$build/linux/sysroot_scripts/install-sysroot.py
# 再次执行gn
$gn gen out/Default
# 出现如下信息则成功
# .gclient file in parent directory /root/quic_stuff/proto-quic might not be the file you want to use
# Done. Made 276 targets from 97 files in 240ms

使用ninja编译源码

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
# cd 进入 quic_stuff/proto-quic/src
$ninja -C out/Default quic_client quic_server

# -----问题1. 如果出现如下错误:
# ninja: Entering directory `out/Default'
# ninja: fatal: ninja version (1.6.0) incompatible with build file ninja_required_version version (1.7.2).
#
# 说明ninja版本太低,解决方法源码编译生成新版本ninja
# cd 进入 quic_stuff
$git clone git://github.com/ninja-build/ninja.git && cd ninja
$git checkout release
$./configure.py --bootstrap
# 编译完成后会在 quic_stuff/ninja 目录下生成ninja可执行文件

# 用新的ninja再次编译
# cd 进入 quic_stuff/proto-quic/src
$~/quic_stuff/ninja/ninja -C out/Default quic_client quic_server
# 如果没有报错并且在out/Default目录下生成了quic_server和quic_client则编译成功了。

运行quic_server和quic_client

基本上按照 https://www.chromium.org/quic/playing-with-quic 的步骤来就可以了。以下是简单描述:

准备测试用的网页

1
2
3
$mkdir /tmp/quic-data
$cd /tmp/quic-data
$wget -p --save-headers https://www.example.org

编辑下载下来的index.html文件,如果headers中存在Transfer-Encoding: chunkedAlternate-Protocol: ...则删除掉。
并且在headers的末尾追加一行X-Original-Url: https://www.example.org/

生成证书

1
2
# cd 进入 quic_stuff/proto-quic/src/net/tools/quic/certs
$./generate-certs.sh

运行quic_server

1
2
3
4
./out/Default/quic_server \
--quic_response_cache_dir=/tmp/quic-data/www.example.org \
--certificate_file=net/tools/quic/certs/out/leaf_cert.pem \
--key_file=net/tools/quic/certs/out/leaf_cert.pkcs8

运行quic_client

1
./out/Default/quic_client --host=127.0.0.1 --port=6121 https://www.example.org/

简单测试大量数据的持续性发送的方法

编辑/tmp/quic-data/www.example.org/index.html

标签中增加文本内容,并且保证Headers中的Content-Length字段的值要大于http body中内容的大小。

值得注意的是,官方网站上明确说明,这两个demo是为了功能演示用的,不能大规模运用,所以这样的测试结果只能做个参考。

编译release版本

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
# 编辑 proto-quic/src/build/config/compiler/BUILD.gn
# 把1589行中的-O0修改成-O2
# 我的方法比较hack,我估计gn和ninja应该可以传入配置来选择相应的config。

1572 # Turn off optimizations.
1573 config("no_optimize") {
1574 if (is_win) {
1575 cflags = [
1576 "/Od", # Disable optimization.
1577 "/Ob0", # Disable all inlining (on by default).
1578 "/GF", # Enable string pooling (off by default).
1579 ]
1580 } else if (is_android && !android_full_debug) {
1581 # On Android we kind of optimize some things that don't affect debugging
1582 # much even when optimization is disabled to get the binary size down.
1583 if (is_clang) {
1584 cflags = [ "-Oz" ] + common_optimize_on_cflags
1585 } else {
1586 cflags = [ "-Os" ] + common_optimize_on_cflags
1587 }
1588 } else {
1589 cflags = [ "-O2" ]
1590 ldflags = []
1591 }
1592 }

同步chromuim中的最新代码至proto-quic

1
2
# cd 进入 proto-quic
$./proto_quic_tools/sync.sh

但是由于我的云主机不能翻墙,所有下载失败了。

其他

按官方的说法,proto-quic目前在linux下只支持ubuntu系统。

参考链接

本文完,作者yoko,尊重劳动人民成果,转载请注明原文出处: https://pengrl.com/p/31237/

0%