首发于自學筆記
调试Flutter Native Engine初探

调试Flutter Native Engine初探

关注Flutter其实也挺久了,但是之前一直只是在Flutter的framework或者界面那里初浅的看了一下,最近因为发现engine里面有些代码和blink和cc里面的有些相似,所以想跟踪一下C++的代码,因为之前一直是写PC端浏览器所以对安卓native的调试也只是一个新手因此特意记录一下

首先依据 flutter/engine中的指导将engine相关的代码下载以及更新完成·,然后根据Android (cross-compiling from Mac or Linux)这一段将代码编译出来,因为我自己为了调试安卓源代码所以给手机刷了arm的asop,因此我会执行下面这条命令

flutter/tools/gn --android --android-cpu arm --unoptimized

紧接着进入到你代码的flutter目录(例如我的位置是path/engine/src/flutter)中的example然后调用

(确保按照Get Started: Install on Linux中将flutter环境设置好)

flutter run --local-engine-src-path /absolute path/to/engine/src --local-engine=android_debug_unopt

(终端在这里会卡住另外新开启终端),这样flutter就会把其中关键的flutter.so给打入到你的apk并且安装到手机上这时候就要放出lldb了。


首先你要确定已经将SDK Tools中的工具都安装完成

紧接着就可以到SDK的安装目录下会有一个lldb的目录在其中找到android文件夹找到调试手机相应的平台(手机需要root,或者直接用x86的模拟器也可以)。然后执行命令

adb push lldb-server /data/local/tmp/ 

将lldb-server放到手机上,然后紧接着执行

adb shell /data/local/tmp/lldb-server platform --server --listen unix-abstract:///data/local/tmp/debug.sock

这条命令这时候整个终端会阻塞在这里你就i可以完全不需要理它了(如果提示Permission denied只需要执行

adb shell chmod 777 /data/local/tmp/lldb-server

将权限改为777就可以了,然后新开一个另外的终端执行lldb进入到调试界面并且执行platform select remote-android看是否支持安卓的远程调试,我本机的llvm6.0版本所以没什么问题。然后执行

platform connect unix-abstract-connect:///data/local/tmp/debug.sock

你会看到之前server的终端会提示有client连上来了,这时候你就可以通过另外的终端查找到你需要attach的运行的flutter 例子的进程号了然后执行以下命令进行挂载

process attach -p xxxx

好了,现在其实调试器已经挂在上去了,问题是现在应该如何使用lldb进行源码级别的调试,

其实当你在为android交叉编译so并且是debug版本时候你会发现flutter.so其实非常的大,因为其中包含许多的调试信息,如果你安装了llvm那么可以通过llvm-dwarfdump-6.0对其进行查看会发现有许多例如.debuginfo .debugline等的描述,具体的格式和说明可以参考以下两遍文章大致了解

DWARF, 说不定你也需要它哦www.jianshu.com图标http://blog.techveda.org/howsourcedebuggerswork/blog.techveda.org

那么既然推送到手机的flutter.so是包含了调试信息的那么其实我们需要做的事情就是就是两部把编译的符号告诉调试器,执行以下命令就可以了

add-dsym /Users/CaiHuan/xxx/src/out/android_debug_unopt/flutter.so

接下来就是把源代码和符号路径作一个关联就可以了

settings set target.source-map /Users/CaiHuan/xx/src/ /Users/CaiHuan/xx/src/out/android_debug_unopt

第一个参数的意思是编译时候的目录信息,第二个参数是你机器上的源码存放路径,都是绝对路径。

这时候源码和符号其实已经关联起来了,你只需要通过lldb进行下断点了,例如我想看看engine在BeginFrame的时候的逻辑那么我找到engine.cc然后知道需要下断点的行数

br s -f engine.cc -l 164

然后执行continue在手机触发一下,你就会发现已经在lldb这里源代码断点断下来了,这时候你就可以对你感兴趣的Flutter的engine进行native c++的调试来观察他的整个渲染的过程了

因为这只是初步梳理lldb的调试流程所以在终端里面进行native的源码调试还是有些简陋,接下来的学习中我会通过vscode的lldb插件配置能够在vscode中进行Flutter的engine调试,并且开始自己初浅的Flutter的Engine分析过程

编辑于 2018-06-29

文章被以下专栏收录