Chromium代码下载编译

https://chromium.googlesource.com/chromium/src/+/main/docs/linux/build_instructions.md

配置编译工具

$ git clone https://chromium.googlesource.com/chromium/tools/depot_tools.git
export PATH="$PATH:${PWD}/depot_tools"

下载编译代码

mkdir chromium && cd chromium

fetch --nohooks chromium

cd src

./build/install-build-deps.sh


gclient runhooks
#这个过程中会安装sysroot,比如:
# src/build/linux/sysroot_scripts/install-sysroot.py --arch=x86

```bash
# 创建out/Default/args.gn,或者gn后面跟args参数
mkdir -p out/Default/
vim out/Default/args.gn # 将下面的选项写到args.gn文件
is_debug=false
 target_cpu="x64"
 target_os="linux"
 use_vaapi=true
 is_component_ffmpeg=true
 media_use_ffmpeg=true
 ffmpeg_branding="Chrome"
 proprietary_codecs=true
 enable_platform_hevc=true
 enable_mse_mpeg2ts_stream_parser=true
 mojo_media_host="gpu"
 mojo_media_services=["video_decoder"]
 is_official_build=false
 enable_nacl=false
 symbol_level=1
 v8_symbol_level=0
 use_ozone=true
 ozone_platform_wayland=true
 ozone_platform_x11=true
 ozone_platform_headless=true
 ozone_auto_platforms=false

生成out/Default/build.ninja文件:

gn gen out/Default

或者,直接通过–args参数指定编译选项,直接生成out/Default/build.ninja:

gn gen --args='is_debug=false
                target_cpu="x64"
                target_os="linux"
                use_vaapi=true
                is_component_ffmpeg=true
                media_use_ffmpeg=true
				ffmpeg_branding="Chrome"
                proprietary_codecs=true
                enable_platform_hevc=true
                enable_mse_mpeg2ts_stream_parser=true
                mojo_media_host="gpu"
                mojo_media_services=["video_decoder"]
                is_official_build=false
                enable_nacl=false
                symbol_level=1
                v8_symbol_level=0
				use_ozone=true
                ozone_platform_wayland=true
                ozone_platform_x11=true
                ozone_platform_headless=true
                ozone_auto_platforms=false' out/Default

编译:

autoninja -C out/Default chrome -v

运行chrome,使用x11启动,播放一个1080的视频:

./out/Default/chrome --no-sandbox --enable-features=UseOzonePlatform --ozone-platform=x11 --app="http://192.168.31.124/stream/mse-demo/1080p.html"

输出log

编译完成后生成chrome,启动命令行加上--enable-logging --v=1开关,就会生成chrome_debug.log,每启动一次log就会被覆盖。

v=1:level 1以下的INFO,WARNING,ERROR都会输出,如果要输出level 2以上,需要指定v=2以上。

./out/Default/chrome --no-sandbox --enable-features=UseOzonePlatform --ozone-platform=x11  --enable-logging --v=1 --app="http://192.168.31.124/stream/mse-demo/1080p.html"

使用wayland启动chromium

chromium使用ozone作为图像输出的平台抽象层,通过ozone-platform选项定义,选择不同标准的协议来支持不同的显示后端,如果需要使用wayland就要指定--ozone-platform=wayland,前面编译的gn参数里面ozone_platform_wayland=trueozone_platform_x11=true,已经支持了wayland和x11,所以启动的时候指定wayland还是x11即可,wayland启动的时候要先启动weston作为wayland server。

--ozone-platform=wayland  // wayland显示协议的支持

--ozone-platform=x11      // 支持X11 Windows系统
./out/Default/chrome --no-sandbox --enable-features=UseOzonePlatform --ozone-platform=wayland  --enable-logging --v=1 --app="http://192.168.31.124/stream/mse-demo/1080p.html"

weston drm启动chromium,默认走硬件egl,gdm无法创建正确的显示buffer,可以通过参数--use-gl切换到swiftshader,通过cpu软件模拟egl的功能,不走硬件egl,来暂时绕过。

./chrome --no-sandbox --enable-features=UseOzonePlatform --ozone-platform=wayland --use-gl=swiftshader

或者chromium编译选项中禁止gbm:

use_wayland_gbm=false

weston参数

weston默认为drm作为后端,可以通过参数 --backend=**-backend.so 来指定后端:

drm-backend.so        // Weston的输出界面,通过/dev/dri/card0节点来显示

x11-backend.so        // Weston的输出,将被作为一个X Windows送到X Server中去显示

wayland-backend.so    // Weston的输出,作为另一个weston的输入,以wayland client的身份运行,需要先启动一个weston

xwayland

它不是一个backend,只是wayland的一个功能拓展,可以在weston中运行X程序,需要weston启动参数–modules=xwayland.so

内部会启动一个X server,用来运行X程序,由于X server又是运行在Wayland server上,所有X server的输出最终是作为一个Wayland Client送去显示的。

weston --modules=xwayland.so

chromium的默认显示backend是x11,因此,最终通过weston xwayland来显示chromium:

./out/build/chrome --enable-accelerated-video-decode --enable-logging --v=1 \
--enable-features=UseOzonePlatform --ozone-platform=wayland --use-gl=egl

启用mojo video_decoder

media/gpu目录是运行在GPU进程中GPU video解码硬件加速的代码,包括不同平台的硬件加速框架和驱动的对接,平台和框架包括

  • vaapi对接x86平台
  • v4l2对接linux平台
  • android平台对接MediaCodec
  • windows平台对接dxva框架
  • mac平台vt框架
  • Render进程和GPU进程通过mojom IPC机制,Render进程作为client,GPU进程运行MojoVideoDecoderService

mojo build args

--- a/media/mojo/BUILD.gn
+++ b/media/mojo/BUILD.gn
@@ -10,13 +10,13 @@ import("//testing/test.gni")
 buildflag_header("buildflags") {
   header = "buildflags.h"
 
-  enable_mojo_renderer = false
+  enable_mojo_renderer = true
   enable_mojo_cdm = false
   enable_mojo_audio_decoder = false
   enable_mojo_audio_encoder = false
-  enable_mojo_video_decoder = false
+  enable_mojo_video_decoder = true
   enable_mojo_media_in_browser_process = false
-  enable_mojo_media_in_gpu_process = false
+  enable_mojo_media_in_gpu_process = true

通过gn参数mojo_media_host指定,设置media component运行在GPU进程。

mojo_media_host = "gpu"

mojo_media_services = ["video_decoder"]

enable_platform_hevc->proprietary_codecs->ffmpeg_branding之间存在这样的依赖关系

启用硬件video decoder

args.gn选项:

flags = [
    "USE_VAAPI=$use_vaapi",
    "USE_VAAPI_IMAGE_CODECS=$use_vaapi_image_codecs",
    "USE_V4L2_CODEC=$use_v4l2_codec",
    "USE_LIBV4L2=$use_v4lplugin",
    "USE_VAAPI_X11=$use_vaapi_x11",
  ]

所以args.gn里面可以用这些选项启用:

use_vaapi = true
use_vaapi_image_codecs = true
use_v4l2_codec = true
use_v4lplugin = true
use_vaapi_x11 = true

编译项说明

target_os="linux":构建系统是win、android、linux、chromeos等

target_cpu=“x86”:x86构建比x64构建快一点,并且支持增量链接以实现更多目标。

enable_nacl=false:不支持本地客户端Native Client (NaCl),这是一种Chrome插件,因为安全性,稳定性存在问题,已经很少使用了。

symbol_level=1:将为堆栈跟踪生成足够的信息,但不会逐行调试。设置symbol_level=0将不包括调试符号。

is_debug=true:GN生成一个启用了所有调试断言,并包含完整调试信息

is_component_build=false:这会使用更多,更小的DLL和增量链接,与is_official_build不能同时为true。

is_official_build=false:指明不使用Chrome官方的编译优化建议。

proprietary_codecs:指明支持H264编码,编译时,自动H264相关组件,打包PE文件中。

remove_webcore_debug_symbols=true:指明删除内核层支持调试的符号文件,这样,有助于减少文件体积,提高运行速度。

blink_symbol_level=0:关闭源级调试以减少闪烁,以减少构建时间,如果您不打算调试闪烁,则可以使用此选项。

qtcreate debug

/home/hui/disk4t/chromium/chromium-2/src/out/Default/chrome --enable-features=UseOzonePlatform --ozone-platform=x11 --enable-nacl --enable-nacl-debug --no-sandbox

build error

error1:undefined symbol: ui::ShellDialogLinux

ld.lld: error: undefined symbol: ui::ShellDialogLinux::SetInstance(ui::ShellDialogLinux*)
>>> referenced by linux_ui.cc
>>>               views/linux_ui.o:(views::LinuxUI::SetInstance(std::__1::unique_ptr<views::LinuxUI, std::__1::default_delete<views::LinuxUI> >)) in archive obj/ui/views/libviews.a

ld.lld: error: undefined symbol: ui::ShellDialogLinux::ShellDialogLinux()
>>> referenced by linux_ui.cc
>>>               views/linux_ui.o:(views::LinuxUI::LinuxUI()) in archive obj/ui/views/libviews.a

ld.lld: error: undefined symbol: ui::ShellDialogLinux::~ShellDialogLinux()
>>> referenced by linux_ui.cc
>>>               views/linux_ui.o:(views::LinuxUI::~LinuxUI()) in archive obj/ui/views/libviews.a
clang++: error: linker command failed with exit code 1 (use -v to see invocation)
ninja: build stopped: subcommand failed.

增加use_gtk就可以了:

use_gtk = true

参考链接

GN-Configuration-notes

building Chromium on Linux

Development Guides