@@ -61,22 +61,51 @@ samples/{source}/{model_name}/
6161
6262## 3. 系统架构设计
6363
64- ### 3.1 目录结构
64+ ### 3.1 核心设计原则
65+
66+ ** 重要:转换器必须实现为 CompilerBackend**
67+
68+ 整个转换器需要实现为 ` GraphCompilerBackend ` 接口,以便:
69+ 1 . ** 复用现有测试流程** :转换后的样本可以直接通过 ` graph_net.paddle.test_compiler ` 流程进行测试
70+ 2 . ** 获得 ES 评估指标** :通过 ` test_compiler ` 流程生成的日志,可以被 ` analysis_util ` 解析并计算 ES(t) 指标
71+ 3 . ** 统一接口** :与其他编译器后端(如 CinnBackend、NopeBackend)保持一致,便于集成和管理
72+
73+ ** 实现位置** :
74+ - 转换器 Backend:` graph_net/paddle/backend/torch_to_paddle_backend.py `
75+ - 注册到 ` graph_net/paddle/test_compiler.py ` 的 ` registry_backend ` 中
76+
77+ ** 工作流程** :
78+ ```
79+ 1. 转换阶段(convert.py):
80+ - 将 PyTorch 样本转换为 Paddle 格式
81+ - 保存到 torch_to_paddle_samples/ 目录
82+
83+ 2. 测试阶段(通过 test_compiler):
84+ - 使用 TorchToPaddleBackend 作为编译器后端
85+ - 运行 graph_net.paddle.test_compiler --compiler torch_to_paddle
86+ - 生成标准格式的测试日志
87+
88+ 3. 评估阶段(通过现有工具):
89+ - 使用 analysis_util 解析测试日志
90+ - 使用 plot_ESt.py 计算和绘制 ES(t) 曲线
91+ - 获得转换结果的完整评估指标
92+ ```
93+
94+ ### 3.2 目录结构
6595
6696```
6797tools/torch_to_paddle/
6898├── __init__.py
6999├── convert.py # 转换主脚本
70- ├── test.py # 测试主脚本
71100├── utils.py # 工具函数模块
72101├── file_processors.py # 文件处理模块
73102└── logs/ # 日志目录(gitignore)
74- ├ ── conversion/ # 转换日志
75- │ ├── {timestamp}_conversion_summary.json
76- │ └── {sample_name}_conversion.log
77- └── testing/ # 测试日志
78- ├── {timestamp}_testing_summary.json
79- └── {sample_name}_test.log
103+ └ ── conversion/ # 转换日志
104+ ├── {timestamp}_conversion_summary.json
105+ └── {sample_name}_conversion.log
106+
107+ graph_net/paddle/backend/
108+ └── torch_to_paddle_backend.py # CompilerBackend 实现
80109```
81110
82111### 3.2 模块设计
@@ -173,35 +202,94 @@ python -m tools.torch_to_paddle.convert \
173202 [--dry-run]
174203```
175204
176- #### 3.2.4 test .py - 测试主脚本
205+ #### 3.2.4 torch_to_paddle_backend .py - CompilerBackend 实现
177206
178207** 功能** :
179- - 读取转换后的样本目录
180- - 对每个样本运行 Paddle 验证测试
181- - 记录测试日志和失败案例
182- - 生成测试报告和 ` torch_to_paddle_samples_list.txt `
208+ - 实现 ` GraphCompilerBackend ` 接口
209+ - 在 ` __call__ ` 方法中加载转换后的 Paddle 模型
210+ - 提供 ` synchronize ` 方法用于性能测试
183211
184- ** 工作流程** :
212+ ** 关键实现** :
213+ ``` python
214+ from graph_net.paddle.backend.graph_compiler_backend import GraphCompilerBackend
215+ import paddle
216+
217+ class TorchToPaddleBackend (GraphCompilerBackend ):
218+ """
219+ Backend for testing PyTorch-to-Paddle converted models.
220+
221+ This backend loads the converted Paddle model and returns it directly,
222+ allowing test_compiler to evaluate the conversion quality through
223+ standard ES(t) metrics.
224+ """
225+ def __call__ (self , model , input_spec = None ):
226+ """
227+ Return the converted Paddle model directly.
228+
229+ The model is already in Paddle format (converted from PyTorch),
230+ so we just return it as-is for testing.
231+ """
232+ return model
233+
234+ def synchronize (self ):
235+ """ Synchronize device operations for accurate timing."""
236+ if (
237+ paddle.device.is_compiled_with_cuda()
238+ or paddle.device.is_compiled_with_rocm()
239+ or paddle.device.is_compiled_with_xpu()
240+ ):
241+ paddle.device.synchronize()
185242```
186- 1. 扫描转换后的样本目录
187- 2. 对每个样本:
188- a. 运行 graph_net.paddle.validate
189- b. 捕获测试结果(成功/失败)
190- c. 记录测试日志
191- 3. 生成汇总报告
192- 4. 生成 torch_to_paddle_samples_list.txt(剔除失败样本)
243+
244+ ** 注册方式** :
245+ 在 ` graph_net/paddle/test_compiler.py ` 中注册:
246+ ``` python
247+ from graph_net.paddle.backend.torch_to_paddle_backend import TorchToPaddleBackend
248+
249+ registry_backend = {
250+ " cinn" : CinnBackend(),
251+ " nope" : NopeBackend(),
252+ " torch_to_paddle" : TorchToPaddleBackend(), # 新增
253+ }
193254```
194255
195- ** 命令行接口** :
256+ #### 3.2.5 测试流程(通过 test_compiler)
257+
258+ ** 重要:复用现有 test_compiler 流程**
259+
260+ 转换后的样本** 不需要** 单独的测试脚本,而是直接通过现有的 ` test_compiler ` 流程进行测试:
261+
262+ ** 测试命令** :
196263``` bash
197- python -m tools.torch_to_paddle.test \
198- --samples-dir torch_to_paddle_samples \
199- --log-dir tools/torch_to_paddle/logs/testing \
200- [--parallel-workers 4] \
201- [--timeout 300] \
202- [--skip-validation]
264+ # 批量测试转换后的样本
265+ python -m graph_net.paddle.test_compiler \
266+ --compiler torch_to_paddle \
267+ --model-path torch_to_paddle_samples/{source}/{model_name} \
268+ --device gpu \
269+ --warmup 10 \
270+ --repeat 100 \
271+ --log-prompt " [Processing] {model_name}"
272+ ```
273+
274+ ** 测试输出** :
275+ - 测试日志会输出到标准输出或指定日志文件
276+ - 日志格式与现有 test_compiler 完全一致
277+ - 包含性能数据(speedup)、正确性数据(correctness)、数据类型(datatype)等
278+
279+ ** ES 评估指标获取** :
280+ ``` bash
281+ # 使用 plot_ESt.py 分析测试日志,获得 ES(t) 指标
282+ python -m graph_net.plot_ESt \
283+ --benchmark-path torch_to_paddle_samples/ \
284+ --output-dir results/
203285```
204286
287+ ** 优势** :
288+ 1 . ** 统一接口** :与其他编译器后端使用相同的测试流程
289+ 2 . ** 自动评估** :测试日志自动包含所有 ES(t) 计算所需的数据
290+ 3 . ** 无需额外开发** :不需要开发单独的测试脚本
291+ 4 . ** 结果可比** :转换结果可以直接与其他编译器后端的结果对比
292+
205293## 4. 详细设计
206294
207295### 4.1 PaConvert 集成策略
@@ -299,26 +387,77 @@ def convert_graph_net_json(source_path, target_path, log):
299387
300388### 4.3 测试验证设计
301389
302- #### 4.3.1 测试流程
303- 使用现有的 ` graph_net.paddle.validate ` 模块进行验证:
390+ #### 4.3.1 测试流程(通过 test_compiler)
391+
392+ ** 核心原则:复用现有 test_compiler 流程**
304393
394+ 转换后的样本通过 ` graph_net.paddle.test_compiler ` 进行测试,使用 ` TorchToPaddleBackend ` 作为编译器后端。
395+
396+ ** 测试流程** :
305397``` python
306- def test_single_sample (sample_path , log ):
307- """
308- 1. 构建验证命令:
309- python -m graph_net.paddle.validate --model-path {sample_path}
310- 2. 执行命令并捕获输出
311- 3. 解析输出判断成功/失败
312- 4. 记录测试日志
313- 5. 返回测试结果
314- """
398+ # test_compiler 内部流程(已存在)
399+ 1 . 加载转换后的 Paddle 模型(model.py)
400+ 2 . 加载输入和权重数据(input_meta.py, weight_meta.py)
401+ 3 . 使用 TorchToPaddleBackend 编译模型
402+ 4 . 运行 Eager 模式基准测试
403+ 5 . 运行 Compiled 模式测试(使用 TorchToPaddleBackend)
404+ 6 . 比较输出正确性(使用 tolerance 配置)
405+ 7 . 测量性能(speedup)
406+ 8 . 输出标准格式日志
407+ ```
408+
409+ ** 日志格式** (与现有 test_compiler 完全一致):
410+ ```
411+ [Processing] {model_name}
412+ [Config] model_path: {path}
413+ [Config] compiler: torch_to_paddle
414+ [Performance][eager]: {...}
415+ [Performance][compiled]: {...}
416+ [Datatype][eager]: [...]
417+ [Datatype][compiled]: [...]
418+ [Correctness][[equal]]: [...]
419+ [Correctness][[all_close_atol_..._rtol_...]]: [...]
420+ [Speedup][e2e]: {value}
421+ [Speedup][gpu]: {value}
422+ [Result] status: success|failed
315423```
316424
317- #### 4.3.2 错误分类
318- - ** 编译错误** :语法错误、导入错误
319- - ** 运行时错误** :执行时异常
320- - ** 验证失败** :graph_hash 不匹配等
321- - ** 超时** :测试执行超时
425+ #### 4.3.2 ES 评估指标获取
426+
427+ ** 通过现有工具链自动获得** :
428+
429+ 1 . ** 解析测试日志** :
430+ ``` python
431+ # 使用 analysis_util 解析日志
432+ samples = analysis_util.parse_logs_to_data(log_file)
433+ ```
434+
435+ 2 . ** 计算 ES(t) 指标** :
436+ ``` python
437+ # 使用 calculate_s_scores 计算 ES(t)
438+ s_scores, es_scores = analysis_util.calculate_s_scores(
439+ samples, folder_name, negative_speedup_penalty, fpdb
440+ )
441+ ```
442+
443+ 3 . ** 绘制 ES(t) 曲线** :
444+ ``` bash
445+ python -m graph_net.plot_ESt \
446+ --benchmark-path {log_file_or_dir} \
447+ --output-dir results/
448+ ```
449+
450+ ** 优势** :
451+ - ** 无需额外开发** :完全复用现有的评估工具链
452+ - ** 结果可比** :转换结果的 ES(t) 指标可以直接与其他编译器后端对比
453+ - ** 自动化** :测试和评估流程完全自动化
454+
455+ #### 4.3.3 错误分类
456+ - ** 编译错误** :语法错误、导入错误(在 test_compiler 中捕获)
457+ - ** 运行时错误** :执行时异常(在 test_compiler 中捕获)
458+ - ** 正确性失败** :输出不匹配(通过 tolerance 检查)
459+ - ** 性能问题** :speedup < 1(在 ES(t) 计算中考虑)
460+ - ** 超时** :测试执行超时(test_compiler 支持 timeout 参数)
322461
323462### 4.4 日志和报告设计
324463
@@ -395,34 +534,40 @@ def test_single_sample(sample_path, log):
395534- 转换策略调整建议
396535
397536### 5.2 阶段 2:核心功能实现(3-5 天)
398- ** 目标** :实现基本的转换和测试功能
537+ ** 目标** :实现基本的转换功能和 CompilerBackend
399538
400539** 任务** :
4015401 . 实现 ` file_processors.py ` 模块
4025412 . 实现 ` convert.py ` 主脚本
403- 3 . 实现 ` test.py ` 主脚本
404- 4 . 实现 ` utils.py ` 工具函数
405- 5 . 实现日志和报告生成功能
542+ 3 . 实现 ` torch_to_paddle_backend.py ` (CompilerBackend 接口)
543+ 4 . 在 ` test_compiler.py ` 中注册新 backend
544+ 5 . 实现 ` utils.py ` 工具函数
545+ 6 . 实现日志和报告生成功能
406546
407547** 输出** :
408548- 可运行的转换脚本
409- - 可运行的测试脚本
410- - 初步的转换和测试结果
549+ - 可用的 TorchToPaddleBackend
550+ - 初步的转换结果
551+ - 通过 test_compiler 测试转换后的样本
411552
412553### 5.3 阶段 3:完善和优化(2-3 天)
413- ** 目标** :处理边界情况,优化错误处理
554+ ** 目标** :处理边界情况,优化错误处理,验证 ES 评估流程
414555
415556** 任务** :
4165571 . 处理各种边界情况
4175582 . 优化错误处理和日志记录
4185593 . 实现并行处理(如需要)
4195604 . 完善报告生成
4205615 . 生成模型列表文件
562+ 6 . ** 验证 test_compiler 流程** :确保转换后的样本可以通过 test_compiler 正常测试
563+ 7 . ** 验证 ES 评估** :使用 plot_ESt.py 验证能够正确计算 ES(t) 指标
421564
422565** 输出** :
423- - 完善的转换和测试工具
424- - 完整的转换和测试报告
566+ - 完善的转换工具
567+ - 完整的转换报告
425568- 两个模型列表文件
569+ - 通过 test_compiler 测试的日志
570+ - ES(t) 评估结果
426571
427572### 5.4 阶段 4:文档和提交(1 天)
428573** 目标** :完善文档,准备 PR
@@ -485,9 +630,11 @@ def test_single_sample(sample_path, log):
485630- 失败案例有明确的错误分类
486631
487632### 7.2 测试阶段
633+ - ** 通过 test_compiler 测试** :转换后的样本能够通过 ` test_compiler --compiler torch_to_paddle ` 正常测试
488634- 测试成功率 > 60%(在转换成功的样本中)
489- - 所有测试结果都有详细日志
635+ - 所有测试结果都有详细日志(标准 test_compiler 格式)
490636- 失败案例有明确的错误分类
637+ - ** ES 评估指标** :能够通过 ` plot_ESt.py ` 正确计算和绘制 ES(t) 曲线
491638
492639### 7.3 文档和交付
493640- 完整的设计文档
@@ -523,6 +670,16 @@ def test_single_sample(sample_path, log):
523670- Paddle 验证工具:` graph_net/paddle/validate.py `
524671
525672### 9.2 参考实现
526- - 现有的测试脚本:` graph_net/paddle/test_target_device.py `
527- - 样本检查工具:` tools/check_and_count_samples.py `
673+ - ** CompilerBackend 实现** :
674+ - ` graph_net/paddle/backend/nope_backend.py ` :最简单的 Backend 实现示例
675+ - ` graph_net/paddle/backend/cinn_backend.py ` :完整的 Backend 实现示例
676+ - ** test_compiler 流程** :
677+ - ` graph_net/paddle/test_compiler.py ` :Paddle 测试主流程
678+ - ` graph_net/torch/test_compiler.py ` :PyTorch 测试主流程(参考)
679+ - ** ES 评估工具** :
680+ - ` graph_net/plot_ESt.py ` :ES(t) 计算和绘图工具
681+ - ` graph_net/analysis_util.py ` :日志解析和 ES(t) 计算
682+ - ** 其他工具** :
683+ - ` graph_net/paddle/test_target_device.py ` :设备测试脚本
684+ - ` tools/check_and_count_samples.py ` :样本检查工具
528685
0 commit comments