(推荐)Ascend PyTorch Profiler数据采集与分析

Ascend PyTorch Profiler是针对PyTorch框架开发的性能分析工具,通过在PyTorch训练脚本中添加Ascend PyTorch Profiler接口,执行训练的同时采集性能数据,完成训练后直接输出可视化的性能数据文件,提升了性能分析效率。Ascend PyTorch Profiler接口可全面采集PyTorch训练场景下的性能数据,主要包括PyTorch层算子信息、CANN层算子信息、底层NPU算子信息、以及算子内存占用信息等,可以全方位分析PyTorch训练时的性能状态。

采集并解析性能数据

  1. 使用Ascend PyTorch Profiler接口开启PyTorch训练时的性能数据采集。

    在训练脚本(如train_*.py文件)内添加如下示例代码进行性能数据采集参数配置,之后启动训练。下列示例代码中,加粗字段为需要配置的参数、方法、类和函数。
    # 扩展参数,通过扩展配置性能分析工具常用的采集项
    experimental_config = torch_npu.profiler._ExperimentalConfig(
            aic_metrics=torch_npu.profiler.AiCMetrics.PipeUtilization, profiler_level=torch_npu.profiler.ProfilerLevel.Level1, l2_cache=False, data_simplification=False
    )
    
    # 配置性能数据采集参数
    with torch_npu.profiler.profile(
            activities=[
                torch_npu.profiler.ProfilerActivity.CPU,    # 采集框架侧数据开关
                torch_npu.profiler.ProfilerActivity.NPU     # 采集NPU数据开关
                ],
            schedule=torch_npu.profiler.schedule(wait=1, warmup=1, active=2, repeat=2, skip_first=10),    # 设置不同step的行为
            on_trace_ready=torch_npu.profiler.tensorboard_trace_handler("./result"),    # 将采集到的性能数据导出为TensorBoard工具支持的格式
     
            record_shapes=True,    # 算子的InputShapes和InputTypes,Bool类型
            profile_memory=True,    # 算子的内存占用情况,Bool类型
            with_stack=True,    # 算子调用栈,Bool类型
            experimental_config=experimental_config) as prof:
                for step in range(steps):
                    train_one_step(step, steps, train_loader, model, optimizer, criterion)
                    prof.step()
    除了使用tensorboard_trace_handler导出性能数据外,还可以使用以下方式导出:
    with torch_npu.profiler.profile() as prof:
        for step in range(steps):
            train_one_step(step, steps, train_loader, model, optimizer, criterion)
    prof.export_chrome_trace('./chrome_trace_14.json')

    当使用Ascend PyTorch Profiler接口采集的性能数据较大时,若在当前环境直接使用on_trace_ready接口进行自动解析,则可能导致资源占用过大出现卡顿,那么可以取消on_trace_ready接口,在采集完成性能数据后,使用如下方式进行离线解析:

    1. 创建{file_name}.py文件,{file_name}自定义,并编辑如下代码:
      from torch_npu.profiler.profiler import analyse
      
      if __name__ == "__main__":
          analyse("./")

      "./"目录下保存PyTorch性能数据目录{worker_name}_{时间戳}_ascend_pt

    2. 保存文件后执行如下命令解析性能数据:
      python3 {file_name}.py
    • 性能数据会占据一定的磁盘空间,可能存在磁盘写满导致服务器不可用的风险。性能数据所需空间跟模型的参数、采集开关配置、采集的迭代数量有较大关系,须用户自行保证落盘目录下的可用磁盘空间。
    • 更多性能数据采集参数介绍请参见性能分析工具使用指南“PyTorch训练/在线推理场景性能分析”。

  2. 查看采集到的PyTorch训练性能数据结果文件。

    训练结束后,在torch_npu.profiler.tensorboard_trace_handler接口指定的目录下生成Ascend PyTorch Profiler接口的采集结果目录。

    └── localhost.localdomain_139247_20230628101435_ascend_pt    // 解析结果目录,命名格式:{worker_name}_{时间戳}_ascend_pt,默认情况下{worker_name}为{hostname}_{pid}
        ├── profiler_info.json              // 多卡或集群场景命名规则为profiler_info_{Rank_ID}.json,用于记录Profiler相关的元数据
        ├── ASCEND_PROFILER_OUTPUT          // Ascend PyTorch Profiler接口采集性能数据
        │   ├── communication.json         // 为多卡通信或集群等存在通信的场景性能分析提供可视化数据基础,配置experimental_config的profiler_level=torch_npu.profiler.ProfilerLevel.Level1或profiler_level=torch_npu.profiler.ProfilerLevel.Level2生成
        │   ├── communication_matrix.json   // 通信小算子基本信息文件,配置experimental_config的profiler_level=torch_npu.profiler.ProfilerLevel.Level1或profiler_level=torch_npu.profiler.ProfilerLevel.Level2生成
        │   ├── data_preprocess.csv        // 配置experimental_config profiler_level=torch_npu.profiler.ProfilerLevel.Level2生成
        │   ├── kernel_details.csv
        │   ├── l2_cache.csv               // 配置experimental_config的l2_cache=True生成
        │   ├── memory_record.csv
        │   ├── operator_details.csv
        │   ├── operator_memory.csv
        │   ├── step_trace_time.csv        // 迭代中计算和通信的时间统计
        │   └── trace_view.json
        ├── FRAMEWORK                      // 框架侧的性能原始数据,无需关注,data_simplification=True时删除此目录
        │   ├── torch.memory_usage
        │   ├── torch.op_mark
        │   └── torch.op_range
        └── PROF_000001_20230628101435646_FKFLNPEPPRRCFCBA  // CANN层的性能数据,命名格式:PROF_{数字}_{时间戳}_{字符串},data_simplification=True时删除此目录下的原始性能数据
              ├── analyze      // 配置experimental_config的profiler_level=torch_npu.profiler.ProfilerLevel.Level1或profiler_level=torch_npu.profiler.ProfilerLevel.Level2生成
              ├── device_x
              ├── host
              ├── mindstudio_profiler_log
              └── mindstudio_profiler_output
    ├── localhost.localdomain_139247_20230628101435_ascend_pt_op_args // 算子信息统计文件目录,配置experimental_config的record_op_args=True生成
        ├── 进程ID
        │    ├── operator_name+data_type+timestamp.json // 算子信息统计文件

    以上数据文件用户无需打开查看,可使用TensorBoard工具进行性能分析,如需了解详细字段解释请参见

    性能分析工具使用指南中“性能数据文件参考 > Ascend PyTorch Profiler接口采集性能数据说明”。

  3. 使用TensorBoard工具进行性能数据分析。

    可使用以下步骤安装并启动TensorBoard工具,或参见《PyTorch Profiler TensorBoard NPU Plugin》。

    1. 安装依赖。
      pip3 install pandas==1.0.0
      pip3 install tensorboard==2.11.0

      要求pandas >= 1.0.0,tensorboard >= 2.11.0。

    2. 下载TensorBoard工具并安装。
      pip3 install torch_tb_profiler_ascend-0.4.0-py3-none-any.whl
    3. 查看是否安装成功。
      pip3 list | grep torch-tb
      显示如下信息表示安装成功。
      torch-tb-profiler-ascend 0.4.0
    4. 启动工具。
      tensorboard --logdir=./result

      --logdir指定待解析的性能数据目录。

      若是远程服务器启动TensorBoard想要在本机查看性能数据,需使用--bind_all参数。

      tensorboard  --logdir=./result --bind_all
      回显如下:
      I0630 14:08:16.533923 281470215713104 plugin.py:454] Monitor runs begin
      I0630 14:08:16.536316 281470215713104 plugin.py:470] Find run directory /home/pzr
      I0630 14:08:16.539052 281470299730256 plugin.py:552] Load run ..
      I0630 14:08:16.561225 281470299730256 loader.py:73] started all processing
      TensorBoard 2.11.0 at http://localhost:6006/ (Press CTRL+C to quit)
      I0630 14:08:43.961050 281470299730256 plugin.py:556] Run .. loaded
      I0630 14:08:43.961973 281470257721680 plugin.py:493] Add run ..

      加粗位置的URL地址即是用与查看结果数据的页面地址。

    5. 查看性能数据。

      将回显中加粗的URL复制,并使用浏览器访问(若为远端服务器则需要将域名“localhost”替换为远端服务器的IP),进入TensorBoard工具界面。

      图1 工具页面

      工具界面通过左侧侧边栏进行视图切换:

      • Runs(红框①)用于切换展示的性能数据文件。
      • Views(红框②)用于切换右侧性能数据详细视图,TensorBoard主要通过该功能进行性能数据分析,详细分析方法见下文“性能分析方法”。
      • Workers(红框③)、Spans(红框④)用于切换不同进程和不同时间产生的数据。

性能分析方法

TensorBoard工具主要通过如下视图来展示PyTorch性能数据:

详细示例请参见性能分析(Trace View)性能分析(Kernel View)性能分析(Operator View)性能分析(Memory View)性能分析(Distributed View)性能分析(DiffView)

性能比对

为了识别PyTorch训练工程从GPU迁移至NPU后是否出现性能劣化,或了解PyTorch训练工程在NPU上,不同版本之间存在性能差距,可以通过性能比对工具具分析性能劣化点或性能差距。

集群分析工具

集群场景下,基于通信域的通信分析和迭代耗时分析,可以通过cluster_analysis工具的cluster_analysis.py脚本将数据进行汇总后分析。

集群场景多卡间算子性能统计

集群场景下,多卡间的算子情况,只能通过查看每张卡各自的性能数据来了解,不能直观的对比各卡之间算子的性能差异。为了直观查看格卡之间算子的性能差异,请通过cluster_kernels_analysis工具的cluster_op_summary_analysis.py脚本,快速统计并展示各卡之间TopN算子的性能数据。

性能分析(Trace View)

图2 trace_view

图2所示,trace数据主要展示如下区域:

Trace View下的性能数据建议通过观察各个层级上的耗时长短、间隙等判断对应组件、算子是否存在性能问题。

性能分析(Kernel View)

Kernel View为kernel_details.csv文件的TensorBoard可视化呈现,包含在NPU上执行的所有算子的信息,如图13所示。

左侧饼图统计不同名称的kernel总耗时占比;右侧饼图统计在不同加速核上执行时间的占比;下方列表Group By选择Statistic时,展示按kernel的名称汇总统计的执行信息。

图13 Kernel View

列表Group By选择All时,展示所有kerenl执行的明细信息,如图14所示。

图14 Group By选择All

可以根据左侧饼图查看耗时多的算子,根据下方列表的Duration排序确认高耗时的算子。

性能分析(Operator View)

Operator View为operator_details.csv文件的TensorBoard可视化呈现,是统计PyTorch算子在Host侧(下发)和Device侧(执行)的耗时,如图15所示。

图15 Operator View

下方列表为上方饼图的明细呈现,如图16所示。

图16 Group By选择Operator

Group By选择Operator+Input Shape时,列表展示算子的输入Shape信息,如图17所示。

图17 Group By选择Operator+Input Shape

可以先根据耗时信息判断高耗时且存在性能瓶颈的算子,再通过单击View CallStack,呈现算子调用栈信息。以图18为例,MatMul有4种不同的调用栈,单击View call frames,可查看具体的调用栈信息。

图18 View CallStack

通过调用栈信息找到具体调用的代码行。

性能分析(Memory View)

Memory View为operator_memory.csv和memory_record.csv文件的TensorBoard可视化呈现,包含算子级(PTA、GE、PTA+GE)、进程级(APP)内存申请情况信息,如图19所示。

用户可以在内存折线图上进行选择,并通过在折线图上拖动鼠标左键来放大所选范围,右键单击会将绘图重置为初始状态。

图19 Memory View_Operator

从Memory View_Operator图中可以看出算子在每个时刻否内存占用情况,一般来说对一个完整的迭代进行性能数据采集即可看到这个迭代算子内存的生命周期(迭代开始前的内存申请是模型初始化时的内存申请)。

根据算子的内存申请及内存时间,分析相关内存问题,将内存峰值减小。

可以从耗内存最大的算子开始排查,从而减小NPU内存的使用。

若Memory View中出现Size负值或Allocation、Release列空值,详细原因请参见性能分析工具使用指南中“性能数据文件参考 > device目录summary数据 > CANN算子的内存占用明细”中“负值空值说明”。

性能分析(Distributed View)

Distributed View是以communication.json或communication_matrix.json和step_trace_time.csv文件为基础提取的TensorBoard可视化呈现,用于分析分布式运行时,多节点之间的HCCL计算和通信的性能瓶颈和通信效率,如图20所示。

图20 Distributed View

性能分析(DiffView)

DiffView是以trace_view.json文件为基础提取的TensorBoard可视化呈现,可以将两份NPU性能数据进行比较。

进行数据比对需要采集两份性能数据,可以是相同设备不同迭代、相同设备进行网络优化前后、相同设备不同卡之间、相同网络不同硬件平台。如图21所示。

图21 DIFF视图配置

Baseline为基准数据Experimental为待验证的比对数据,Runs指定设备平台、Workers指定不同Profiler进程(即不同的Profiler结果目录,可以是两个迭代分别生成、网络优化前后分别采集或两个卡采集的两份性能数据)、Spans指定同一Profiler进程中不同时间多次采集的时间戳。

图22 DiffView
图23 Operator View

完成Baseline和Experimental配置后,在右侧生成DiffView和Operator View。