as工程放到源码编译_Flutter源码剖析(二):源码的阅读与调试环境配置

综述

Flutter从架构上来说有3部分:

  • 用Dart写的Framework层,面向开发者
  • 用Java/Kotlin写的Embdder层(For Android,iOS是OC/Swift),纯Flutter App不需要关心
  • 用C++写的Engine层,提供Dart运行环境和底层绘制能力

针对每个部分,对应的源码阅读环境不同,调试方法也不同。

对于阅读环境,最重要的是能够正确地完成调用/定义的跳转

对于调试环境,最重要的是能够设置断点,单步执行

Framework环境配置

Framework的环境设置比较简单。

源码阅读

Framework的代码在 https://github.com/flutter/flutter 下面,直接Clone下来。

亲测安装了Flutter插件的Android Studio是最好的阅读工具,直接打开./packages/flutter 目录,然后flutter pub get即可。

这一步可能报错,主要是一些的版本冲突,按照信息解决即可。

源码调试

通过Flutter Acttach按钮即可开始调试,但是如果要调试启动部分的Dart代码,用Debug而不是Run来启动程序:

3be7fe8bf36faa0fbf8ece162f8d51f6.png

Embedder环境配置

Embedder的环境稍微复杂一点。

源码阅读

Embedder的代码在engine的./shell/platform下面:

tree -L 1
.
├── BUILD.gn
├── android
├── common
├── config.gni
├── darwin
├── embedder
├── fuchsia
├── glfw
├── linux
└── windows
540b6a792e07ca933cf6ccc3581d2783.png

用AS直接打开android目录即可,打开后会发现代码都无法解析对,这样就没法跳转了!!!

首先把根目录设置为Source类型:

e71dec61aac8376d03df7beecb654a02.png

这时候只剩androidx无法解析了:

2bb94587607da58066c7eb53427ee65c.png

发现旁边一个目录已经声明了依赖,于是按照提示,建立一个local.properties文件,指出本地sdk路径即可,然后执行Gradle命令,拉取更新:

a8b7708ebca922680c0a98b0f831f719.png

后来查看文档,发现其实另外一个目录已经有这些依赖了,直接在工程设置页面添加一个classpath即可:

../third_party/android_embedding_dependencies/

这个目录是在engine外,buildroot下的,应该是之前gclient sync的时候就解析build.gradle拉下来的。

源码调试

如果在打开Flutter的工程,打开Andorid的Activity是解析错误的:

37d9e35970a9476985c97f595656b1f7.png

需要以android作为根目录单独打开,然后通过Run/Debug按钮再次启动即可:

1b7e2491aa8d915f4973007a5b12e444.png

这里单独打开工程无需担心如何集成Flutter,gradle脚本已经搞定了。

Engine环境配置

Engine的配置是最复杂的。

源码阅读

把gn工具在src/out 目录生成的compile_commands.json文件移到src/flutter目录下,然后用CLion打开这个文件就可以正确索引Engine的C++代码了。

0554238994eb228b6bd99157d909b477.png

该文件是预编译生成的索引,其他编辑器也可以支持,当然用CLion是最方便的。

源码调试

官方提供了gdb的调试方法,但是没有文档,按照代码注释的文档,也无法运行成功,一直报下面的错误:

Could not find platform independent libraries 
Could not find platform dependent libraries 
Consider setting $PYTHONHOME to [:]
ImportError: No module named site

看到网上有人已经在用lldb调试了,于是也按照这个思路成功了,

首先是把Android SDK的lldb-server push到设备,建立一个信道,通过run-as绕过权限问题:

# 注意换成自己的包名
adb push lldb-server /data/local/tmp/lldb-server

adb shell run-as com.example.flutter_demo \
cp -F /data/local/tmp/lldb-server /data/data/com.example.flutter_demo/lldb-server

adb shell run-as com.example.flutter_demo \
chmod a+x /data/data/com.example.flutter_demo/lldb-server

adb shell "run-as com.example.flutter_demo sh -c '/data/data/com.example.flutter_demo/lldb-server platform --server --listen unix-abstract:///data/data/com.example.flutter_demo/debug.socket'"

通过以上几步已经建立可以调试的通道了,然后启动lldb,attach到指定进程(通过进程id),然后添加符号表:

adb shell pidof com.example.flutter_demo
lldb
(下面是lldb环境)
(lldb) platform select remote-android
(lldb) process attach -p 25382
(lldb) add-dsym ~/WorkProject/flutter_source_code/src/out/android_debug_unopt_arm64/libflutter.so

之前就注意到构建目录下的这个so非常大,打包的so不过10M,这个接近300M,应该是存在大量调试信息。

8cc93125cf1c3109a16fbef45fed00c8.png

这里有两个坑:

  1. lldb进去之后,进程会挂起,必须用c/continue来恢复,不然无法触发逻辑,也就无法触发断点
  2. 必须在System.loadLibrary之后才能添加符号表,否则失败,如果还是失败,就把以上流程重试一遍~

如此,便可以开始调试了,下面演示在帧刷新位置设置断点,然后触发:

2507f113307a5a612addf9c6c6adbd8b.png

总结

以上便是Flutter源码阅读/调试环境的搭建,欲善其事,先利其器,后面就要开始真刀真枪撸源码了。

参考

  • engine/flutter_gdb at master · flutter/engine
  • Debugging the engine · flutter/flutter Wiki
  • Debugging Flutter apps - Flutter
  • Debugging Flutter apps programmatically - Flutter
  • Using an OEM debugger - Flutter
  • 如何调试Android Native Framework
  • Flutter Engine C++ 源码调试初探
  • Android 调试桥 (adb)  |  Android 开发者  |  Android Developers

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/557953.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

workbook加载文件路径_【Python】文件重命名(按照Excel清单)

问题:1、扫描了很多文件,想批量加上文件编号2、网页下载了一堆图片,批量加上图片分类3、文件命名不规范,想批量调整效果图:需求解析:1、想重命名,就要有原名字和修改后的名字,清单准…

ppap文件过程流程图制作_收藏 | 据说PPAP的精华都在这个PPT里!一起来鉴定下

一组数字的PPAP3种情况必须提交8种情况通知提交5种提交等级3种提交状态18份提交内容“3”——以下3种情况,必须向顾客提交PPAP:1)一种新的零件或产品;2)对以前所提供不符合零件的纠正;3)由于设计记录、规范或材料方面的工程变更从…

++实现 ipv6数据报_IPV6报文格式和IPV4有什么区别?

前言RFC2460定义了IPv6数据报格式。总体结构上,IPv6数据报格式与IPv4数据报格式是一样的,也是由IP报头和数据(在IPv6中称为有效载荷)这两个部分组成的。但在IPv6数据报数据部分还可以包括0个或者多个IPv6扩展报头(Extension header)。正文1IPV6报文格式如…

曲面设计步骤pdf_3dmax模渲大师|室外设计师怎么用3dmax疯狂模渲大师制作室内设计效果图的外景天空?...

3dmax模渲大师|室外设计师怎么用3dmax疯狂模渲大师制作室内设计效果图的外景天空?这次食住玩讲的是第十三章的第1节,3dmax疯狂模渲大师室外设计篇的第1课——“外景天空”的使用方法。在室内设计效果图领域,也有要涉及室外的时候。…

iphone日历显示周视图_用敬业签记录放假安排 2021年放假安排日历

2021年已经踏着轻快的步伐向我们一路小跑而来,新的一年中,除了可以做更多的成绩之外,还有很多假期伴随而来。做好放假安排就可以让假期更加充实,为了能够更好的记录放假安排和相关事项可用敬业签这款便签软件。使用敬业签记录放假…

人工智能的炒作_为什么人工智能被过度炒作?

像任何新技术一样,人工智能也经历了称为“炒作周期”的各个阶段。它们从技术触发器开始。如果超过了人们设定的期望值(过度夸大),那么就会带来技术未达到预期的幻灭感,然后就是带来启发的成功案例,最后是生产力的稳定期。有了人工…

opencv轮廓周长原理_opencv轮廓逼近的精度参数与周长cvContourPerimeter的汇总

1)CV_Assert():若括号中的表达式值为false,则返回一个错误信息。函数原型是:#define CV_Assert( expr ) if((expr)) ; else cv::error( cv::Exception(CV_StsAssert, #expr, "", __FILE__, __LINE__) )2)cvContourPerimeter&#x…

mysql的所有聚合函数_MySQL 聚合函数(一)聚合(组合)函数概述

MySQL版本:5.7+ 一、MySQL 5.7中的聚合函数 MySQL 5.7中的聚合函数如下: 除非另有说明,否则组合函数会忽略NULL值。 如果在不包含Group By子句的语句中使用组合函数,就等效于对所有行进行分组。(个人理解是,结果总是只有一行。)关于这点的更多信息,后面的小节“MySQL处理…

mysql 转型_MySQL的未来在哪?

阿里云 MySQL&MariaDB 数据库产品结合开源社区,提供了稳定、可靠、便捷、弹性的在线数据库服务,帮助全球企业客户进行数字化转型。MySQL发展经历了一系列变化,从Sun到Oracle,发展也经过了几个阶段。MySQL从5.7版本开始走上了代…

mongoose换成mysql_如何将MongoDB数据库的数据迁移到MySQL数据库中

FAQ v2.0终于上线了,断断续续忙了有2个多月。这个项目是我实践的第一个全栈的项目,从需求(后期有产品经理介入)到架构,再到设计(有征询设计师的意见)、构建(前端、后台、数据库、服务器部署),也是第一次独立负责一个项目&#xff…

java虚拟机——JVM

JVM:java虚拟机,简称JVM,是运行所有java程序的假想计算机,是java程序的运行环境,是java最具吸引力的特征之一。我们编写的java代码,都运行在JVM之上。 跨平台:任何软件的运行,都必须…

mysql 5.0.37.tar.gz_Linux下MySQL5.0.37安装配置步骤

Linux下安装MySQL5.0.37需要以下面三个包:MySQL-client-community-5.0.37-0.rhel3.i386.rpmMySQL-server-community-5.0.37-0.rhel3.i386.rpmperl-DBI-1.53-2.fc7.i386.rpm(以下步骤需要root权限)1.验证是否已经安装过MySQLrpm -qa|grep MySQL如果发现有安装过,并需要卸载,使用…

JRE和JDK

JRE:是java程序的运行时环境,包含JVM和运行时所需要的核心类库。 JDK:时java程序开发工具包,包含JRE和开发人员使用的工具。 我们想要运行一个已有的java程序,那么只需要安装JRE即可。 我们想要开发一个全新的java程序…

java程序开发步骤

java程序开发步骤 开发环境搭建完毕后,可以开发第一个程序了 java程序开发三个步骤:编写,编译,运行。

thinkphp三级分销小程序源码_山东谷道微信小程序商城源码带后台 公众号平台三级分销系统...

山东谷道微信小程序商城源码带后台 公众号平台三级分销系统那么微信二级分销系统与微信三级分销系统到底有什么区别和联系呢?为什么改了个数字地位就天差地别?1、微信分销模式等级的区别用简洁的话来说,微信的三级分销系统包含了微信的二级分销系统,只…

linux mysql timestamp_MySQL时间类型Timestamp和Datetime 的深入理解

MySQL数据库常用的时间类型有timestamp和datetime,两者主要区别是占用存储空间长度不一致、可存储的时间也有限制,但针对不同版本下,timestamp字段类型的设置需要慎重,因为不注意的可能会被“坑死”。一、TIMESTAMP和DATETIME字段…

sql express 无法启动服务_在Windows2012下安装SQL Server 2005无法启动服务的解决办法...

因为安装了Windows2012操作系统,的确很不错,唯一的遗憾就是不支持Sql Server 2005的安装。找了很多办法,基本上都有缺陷。现在终于找到一种完全正常没有缺陷的办法了,和大家分享一下。1、正常安装任一版本的SQL Server 2005.2、安…

ecs php mysql集成环境_在阿里云 CentOS 服务器(ECS)上搭建 nginx + mysql + php-fpm 环境...

阿里云的云服务器(ECS)可以选择多种操作系统,打算用它运行 Drupal或者 WordPress ,你最好选择 Linux 系统,这篇文章的演示是基于阿里云的 CentOS 操作系统的服务器。我们在上面搭建一个 nginx mysql php-fpm 的环境,这就是常说的…

python处理文件夹_python文件及文件夹操作

1.open()各模式详情r 以只读模式打开,没有write()方法,默认打开方式w 以只写模式打开,文件不存在时会自动创建文件,文件已存在时会清除文件内容并重建文件。这种模式打开的文件没有read()方法。a 以追加模式打…

svn中项目管理中ec_Mac中使用svn进行项目管理

Mac中使用svn进行项目管理,借鉴了http://blog.csdn.net/q199109106q/article/details/8655204以下方案多人亲测可用转载请注明出处:http://blog.csdn.net/yc7369在Windows环境中,我们一般使用TortoiseSVN来搭建svn环境。在Mac环境下,由于Mac自…