ArkTS内存快照聚类分析规则
本原创文章帖发布在华为开发者联盟社区欢迎开发者前往访问评论交流更多与该内容相关讨论请点击原帖查看ArkTS内存快照聚类分析规则-华为开发者话题 | 华为开发者联盟一、聚类需求背景在通过ArkTS内存快照定位内存泄漏问题时通常需要优先关注内存占用大的对象这部分对象在快照中占比比较大。当数量较多时存在不同调用点创建的对象因为对象类型被归类在同一目录下如jsobject/jsarray等对象在大型工程中一般情况下拥有10万以上的数量级无法通过人工来快速识别同类型不同业务对象各自占用的内存大小。因此需要聚类规则来指导针对快照的聚类分析将快照中的同类对象进行聚类从而统计出各泄漏对象的影响大小对定位内存泄漏问题有着关键性的指导作用。二、聚类步骤描述1. 确认聚类锚点只聚类top20的目录下的对象 retained size占在5%以上的目录下的对象2. 通过聚类规则对各类对象进行聚类。为了保证聚类结果的有效性不同的目录下存放的对象不同聚类规则也不同。3. 统计各类对象的数量及内存占用大小能够按照对象的数量或内存大小进行排序三、聚类规则聚类规则主要分为三种最短引用链聚类名称聚类属性聚类。不同的对象需要使用不同的聚类方法。注建议所有对象默认按照最短引用链聚类。1. 最短引用链聚类基本类型对象默认按照最短引用链聚类默认适用对象类型Methodjs_setjs_mapstringJSNativePointerjsarray等Methodjs_setMapstringJSNativePointer等目录下对象优先通过引用链聚类。该类对象目录下名称一致通过引用链可以区分对象创建场景。对比目录下各对象到GC ROOT的最短引用链如果有多条最短引用链则选择retained size最大的那条引用链最短引用链相同则视为一类。2. 名字 引用链聚类适用对象类型Function framework(array)各类业务对象业务侧创建的类对象和函数对象业务对象带有路径对象名称和行号信息。相同的类或函数对象调用点不同则引用链不同需要根据不同的调用点进行区分。3. 属性引用链聚类适用对象类型jsobjectjs_shared_objectjsobjectjs_shared_object目录下对象名字相同但代表的对象并不一致需要通过引用链对jsobject对象进行分类即对不同调用点的jsobject进行区分。jsobject对象中存在大量distance为1的对象这些对象无法通过引用链区分但可以通过属性进行区分即直接持有的对象是否一致如果jsobject对象直接持有的对象名称都相同且持有关系紫色的字代表持有关系也相同则归为一类。4.特殊聚类4.1 无需聚类对象类型适用对象SourceTextModule, HiddenClass(NonMovable), global_env, global_objectSourceTextModule对象是系统侧创建的用于持有export对象。每个ts文件会对应生成一个SourceTextModule对象持有该ts文件中export的对象因此天然就已经是聚类后的结果不需要再次聚类。HiddenClass和其他对象是1对多的关系每一个对象都持有一个HiddenClass对象的引用因此每一个HiddenClass都是一类。GlobalEnv和GlobalObject在一份快照中是唯一的因此也无需聚类。4.2 异步任务相关对象适用对象Promise/PromiseRecord/PromiseCapability/PromiseReaction异步相关的对象请根据PromiseReaction下的handle信息最短引用链进行聚类。Promise/PromiseRecord/PromiseCapability 对象为异步任务内部对象开发者无需关注。PromiseReaction下的handle信息代表了该异步任务的下一跳任务可以通过下一跳任务进行区分。4.3 proxyproxy往往与框架对象强相关可以通过proxy下的target信息handle引用链进行聚类。proxy下的target信息代表了proxy持有的被代理对象proxy本身无意义需要根据被proxy代理的对象进行区分。