已合并
【API一致性任务】test: Add consistency validation cases for torch.QUInt4x2Storage.dtype on NPU (#3536) #44411
luoxiaoyan2024创建于 8月12日
【API一致性任务】test: Add consistency validation cases for torch.QUInt4x2Storage.dtype on NPU (#3536) #44411
已合并
luoxiaoyan2024创建于 8月12日
8月12日

欢迎加入社区,感谢您对社区的贡献 🎉!

torch.QUInt4x2Storage.dtype 一致性验证用例 说明

关联 issue:https://gitcode.com/Ascend/pytorch/issues/3536
提交分支:api-3536-v2.7.1(目标 base:v2.7.1)
改动文件:test/test_quint4x2_storage_dtype.py(新增,96 行)

环境信息

验证在 Ascend 910B3 NPU 服务器的 CANN 8.5.1 容器中进行,torch_npu 分别安装于 PyTorch 2.7.1 / 2.11.0 / 2.12.0 三个版本;并按社区最新验收要求在 Ascend 950PR(CANN 9.1.0)环境补充验证(见「运行验证(Ascend 950PR)」);终端运行截图见文末「运行验证」说明与本地交付物。

使用场景及问题

来源任务:https://gitcode.com/Ascend/pytorch/issues/3536

对应 API:torch.QUInt4x2Storage.dtype

torch.quint4x2 是 4-bit 无符号整数量化数据类型(每字节打包 2 个元素),其底层连续存储由 torch.QUInt4x2Storage 承载。API 一致性验收要求该存储类的 dtype 类属性稳定返回 torch.quint4x2,且需在 NPU 环境下验证其取值与 CPU 一致(设备无关)。官方未对该属性建立聚焦的一致性断言,因此需在 test/ 补齐自包含用例。

API 功能

torch.QUInt4x2Storage 是支撑量化数据类型 torch.quint4x2 的底层存储类(Storage)。quint4x2 表示每个元素 4 bit、每字节打包 2 个元素的无符号整数量化类型;QUInt4x2Storage 负责以字节数组形式承载这类量化张量的连续存储。

torch.QUInt4x2Storage.dtype 是该存储类的类级只读属性,返回该存储所承载的量化数据类型,取值恒为 torch.quint4x2。该属性特性:

  • 无入参、只读:不可通过赋值修改;返回值是数据类型对象 torch.quint4x2 自身(identity 一致,is 比较为真)。
  • 设备无关:CPU 与 NPU 环境下取值一致,不随加速器变化。
  • 类 / 实例均可访问:既可通过类 torch.QUInt4x2Storage.dtype 访问,也可通过实例 torch.QUInt4x2Storage().dtype 访问,二者取值相同。

PyTorch 官方用例及完整性

在 PyTorch 官方 test/ 目录中检索(master / v2.7.1 / v2.11.0 / v2.12.0),QUInt4x2Storage / quint4x2 仅在量化相关用例中作为被量化张量的底层存储被间接触及,没有针对 storage.dtype 取值与量化 dtype 集合归属的聚焦一致性断言:

test/test_quantization.py / test/test_type_promotion.py :quint4x2 仅在量化流程中被引用
test/ :0 处独立断言 QUInt4x2Storage.dtype is torch.quint4x2

因此,社区对 QUInt4x2Storage.dtype 的「取值正确性 + 量化 dtype 归属 + 边界区分」覆盖不充分,需新增自包含一致性用例。

NPU 适配分析(含分类判定)

QUInt4x2Storage.dtype 是设备无关的类级只读属性,其取值不依赖任何 NPU kernel 或设备特定代码路径;当前 NPU 未单独注册 torch.npu.QUInt4x2Storage 类(curated NPU storage 列表仅覆盖数值 / bool / bfloat16 类存储),昇腾环境导入 torch_npu 后其行为与 CPU 完全一致。本接口无需修改 TorchNPU 实现、无需 NPU 适配 patch。

因此,本 API 归类为 1.2②:PyTorch 官方社区用例覆盖不充分,且涉及硬件相关存储类接口 → 在 test/ 目录新增一致性验证用例补齐(非修改源码 patch)

新增用例设计(功能一致标准覆盖)

新增 test/test_quint4x2_storage_dtype.py,按 API 功能一致标准以等价类 / 边界值覆盖(无数值计算、无入参):

  • 取值正确性torch.QUInt4x2Storage.dtype is torch.quint4x2;且与空存储实例 .dtype 一致。
  • 量化 dtype 集合归属assertIn{quint8, qint8, qint32, quint4x2}
  • 边界区分assertIsNotquint8 / qint8,避免与相邻量化 dtype 混淆。
  • 设备无关一致性:CPU 与 NPU 环境取值一致(torch.npu.is_available() 守卫);若 NPU 注册 torch.npu.QUInt4x2Storage 额外校验其 .dtype.size()

两个用例 test_cpu_quint4x2_storage_dtype / test_npu_quint4x2_storage_dtype 均带 hasattr 守卫,缺失该存储类的构建会优雅跳过而非报错。

运行验证

验证环境:

操作系统:Ubuntu 22.04.5 LTS
系统架构:aarch64
昇腾硬件:Ascend 910B3,8 卡,Health 为 OK
npu-smi:24.1.0
CANN:8.5.1
Python:3.10(torch_2.7.1 / torch_2.11.0 / torch_2.12.0 验证环境)

在 NPU 环境实跑 python test/test_quint4x2_storage_dtype.py -v,三个版本(2.7.1 / 2.11.0 / 2.12.0)均 Ran 2 tests ... OK,CPU 用例与 NPU 守卫用例实际执行(非跳过)

PyTorch torch-npu 检查项 失败 错误 结果
2.7.1+cpu 2.7.1.post8 2 用例(CPU + NPU 守卫) 0 0 PASS
2.11.0+cu130 2.11.0 2 用例(CPU + NPU 守卫) 0 0 PASS
2.12.0+cu130 2.12.0 2 用例(CPU + NPU 守卫) 0 0 PASS

三个版本(2.7.1 / 2.11.0 / 2.12.0)终端输出一致,完整日志如下:

========== torch 2.7.1 (torch.QUInt4x2Storage.dtype) ==========
$ /root/miniconda3/envs/torch_2.7.1/bin/python /tmp/test_quint4x2_storage_dtype.py -v   # torch 2.7.1+cpu / torch_npu 2.7.1.post8
test_cpu_quint4x2_storage_dtype (__main__.TestQUInt4x2StorageDtype) ... /tmp/test_quint4x2_storage_dtype.py:51: UserWarning: TypedStorage is deprecated. It will be removed in the future and UntypedStorage will be the only storage class. This should only matter to you if you are using storages directly.  To access UntypedStorage directly, use tensor.untyped_storage() instead of tensor.storage()
  self.assertIs(torch.QUInt4x2Storage.dtype, torch.quint4x2)
ok
test_npu_quint4x2_storage_dtype (__main__.TestQUInt4x2StorageDtype) ... ok

----------------------------------------------------------------------
Ran 2 tests in 0.028s

OK

========== torch 2.11.0 (torch.QUInt4x2Storage.dtype) ==========
$ /root/miniconda3/envs/torch_2.11.0/bin/python /tmp/test_quint4x2_storage_dtype.py -v   # torch 2.11.0+cu130 / torch_npu 2.11.0
test_cpu_quint4x2_storage_dtype (__main__.TestQUInt4x2StorageDtype) ... /tmp/test_quint4x2_storage_dtype.py:51: UserWarning: TypedStorage is deprecated. It will be removed in the future and UntypedStorage will be the only storage class. This should only matter to you if you are using storages directly.  To access UntypedStorage directly, use tensor.untyped_storage() instead of tensor.storage()
  self.assertIs(torch.QUInt4x2Storage.dtype, torch.quint4x2)
ok
test_npu_quint4x2_storage_dtype (__main__.TestQUInt4x2StorageDtype) ... ok

----------------------------------------------------------------------
Ran 2 tests in 0.026s

OK

========== torch 2.12.0 (torch.QUInt4x2Storage.dtype) ==========
$ /root/miniconda3/envs/torch_2.12.0/bin/python /tmp/test_quint4x2_storage_dtype.py -v   # torch 2.12.0+cu130 / torch_npu 2.12.0
W0819 01:32:34.165000 32618 root/miniconda3/envs/torch_2.12.0/lib/python3.10/site-packages/torch/_native/cutedsl_utils.py:55] CuTeDSL operators require optional Python packages `nvidia-cutlass-dsl` and `apache-tvm-ffi`; missing optional dependency `nvidia_cutlass_dsl` (importlib.util.find_spec(nvidia_cutlass_dsl) failed)
test_cpu_quint4x2_storage_dtype (__main__.TestQUInt4x2StorageDtype) ... /tmp/test_quint4x2_storage_dtype.py:51: UserWarning: TypedStorage is deprecated. It will be removed in the future and UntypedStorage will be the only storage class. This should only matter to you if you are using storages directly.  To access UntypedStorage directly, use tensor.untyped_storage() instead of tensor.storage()
  self.assertIs(torch.QUInt4x2Storage.dtype, torch.quint4x2)
ok
test_npu_quint4x2_storage_dtype (__main__.TestQUInt4x2StorageDtype) ... ok

----------------------------------------------------------------------
Ran 2 tests in 0.284s

OK

verify_quint4x2_all.png

运行验证(Ascend 950PR 补充验证)

按社区最新验收要求,另在 Ascend 950PR 环境实跑同一用例文件 test/test_quint4x2_storage_dtype.py 取证(该环境当前安装 torch_npu 2.12.0;.dtype 为设备无关类属性,跨版本行为一致):

操作系统:Ubuntu 22.04.5 LTS
系统架构:x86_64
昇腾硬件:Ascend 950PR,1 卡,HBM 128G,Health 为 OK
npu-smi:25.7.rc1.6
CANN:9.1.0
Python:3.10.12
torch / torch_npu:2.12.0+cu130 / 2.12.0

实跑结果:Ran 2 tests ... OK,CPU 用例与 NPU 用例实际执行(非跳过)

环境 torch torch-npu 检查项 失败 错误 结果
Ascend 950PR 2.12.0+cu130 2.12.0 2 用例(CPU + NPU) 0 0 PASS
$ python3 test_quint4x2_storage_dtype.py -v   # 950PR: Ascend950PR / CANN 9.1.0, torch 2.12.0+cu130 / torch_npu 2.12.0
test_cpu_quint4x2_storage_dtype (__main__.TestQUInt4x2StorageDtype) ... /tmp/q4x2_950pr/test_quint4x2_storage_dtype.py:51: UserWarning: TypedStorage is deprecated. It will be removed in the future and UntypedStorage will be the only storage class. This should only matter to you if you are using storages directly.  To access UntypedStorage directly, use tensor.untyped_storage() instead of tensor.storage()
  self.assertIs(torch.QUInt4x2Storage.dtype, torch.quint4x2)
ok
test_npu_quint4x2_storage_dtype (__main__.TestQUInt4x2StorageDtype) ... ok

----------------------------------------------------------------------
Ran 2 tests in 0.003s

OK

verify_quint4x2_950pr.png

950PR 验证结论与 910B3 三版本一致:torch.QUInt4x2Storage.dtype 在两种昇腾硬件(910B3 / 950PR)与 CANN 8.5.1 / 9.1.0 下取值均为 torch.quint4x2,设备无关性成立。

资料检查

torch.QUInt4x2Storage 为标准量化 storage 类、非私有接口、非缺失 API,依 §2 不纳入 native_apis 资料补齐;其所属量化模块在资料中已有收录。本次新增一致性用例不改变支持状态,无需提交资料 PR。

结论

检查项 结论
TorchNPU 环境可验证目标 API(.dtype 取值一致)
接口行为在 NPU 上与 CPU 一致(设备无关)
PyTorch 官方有聚焦 / 完整的 .dtype 一致性用例
需要修改 TorchNPU API 实现
需要新增 NPU 适配 patch
需要在 test/ 新增一致性验证用例
需要补充正式资料

欢迎加入社区,感谢您对社区的贡献 🎉!

likedislike
Pull Request已成功合入, 合并人@ascend-robot
(感谢 luoxiaoyan2024 的贡献)
Lluoxiaoyan2024
8月12日 创建了 pull request,commit 9a0fdd56
Lluoxiaoyan2024
8月12日 关联了issue:【社区任务】7月社区任务第四期-Ascend for PyTorch API 一致性开发(54)
atomgit-bot
atomgit-bot
8月12日 评论:

变更摘要

本 PR 新增了 test/test_quint4x2_storage_dtype.py 测试文件,用于补齐 torch.QUInt4x2Storage.dtype 属性在 CPU 与 NPU 环境下的一致性验证用例。测试类 TestQUInt4x2StorageDtype 包含两个测试方法,分别在 CPU 端校验 dtype 恒为 torch.quint4x2 且与 quint8/qint8 明确区分,以及在 NPU 端验证设备无关的 dtype 属性一致性,并对 NPU 未来可能注册的专属存储类预留了自动扩展校验逻辑。

主要改动

  • 新增 TestQUInt4x2StorageDtype 测试类:继承自 TestCase,作为 torch.QUInt4x2Storage.dtype 一致性验证的测试容器,包含完整的模块文档说明和版权声明。
  • 新增 test_cpu_quint4x2_storage_dtype 用例:通过 hasattr 守卫检查 QUInt4x2Storage 可用性,使用 assertIs 验证 dtype 等于 torch.quint4x2,使用 assertIn 验证其属于量化 dtype 集合(quint8/qint8/qint32/quint4x2),并用 assertIsNotquint8/qint8 做边界区分。
  • 新增 test_npu_quint4x2_storage_dtype 用例:通过 torch.npu.is_available() 守卫 NPU 环境,验证设备无关的 torch.QUInt4x2Storage.dtype 仍为 torch.quint4x2;若 torch.npu.QUInt4x2Storage 存在则额外校验其类属性 dtype 与空实例的 dtype 及存储大小。
  • 入口点集成:文件末尾通过 run_tests() 将用例集成到 PyTorch 测试框架中,确保可被自动化 CI 流水线执行。
likedislike
不准确?
atomgit-bot
atomgit-bot
8月12日 评论:

代码审查

结束总结

优先级 数量
P0 0
P1 0
P2 1
P3 1

各文件审查结果:

  • test/test_quint4x2_storage_dtype.py:发现 2 个问题。一个是 NPU 测试缺少 hasattr(torch, "QUInt4x2Storage") 守卫(P2),与 CPU 测试的防御性编码不一致,在特定构建配置下会导致 AttributeError;另一个是缺少 import torch_npu(P3),使得 NPU 测试路径在独立运行时始终被跳过,且与仓库中其他 NPU 测试文件的约定不一致。

整体风险评估:低风险。 两个问题均不会导致生产级故障或数据损坏。P2 问题仅在 NPU 可用但 QUInt4x2Storage 缺失的罕见构建配置下触发;P3 问题仅导致 NPU 测试路径静默跳过而非崩溃。两个修复都是局部添加防御性代码,改动范围小、风险低。

类型 数量
🔴 阻塞 0
🟡 建议 1

💬 仅评论

likedislike
不准确?
此处折叠了279条消息 查看更多
luoxiaoyan2024
1 天前 评论:

@chenrayray @li_jing_hw 打扰了:本 PR 已获 /lgtm 与 /approve,CI 流水线(#67383,commit f9fe42c8)已通过,当前唯一阻塞是 2026-08-12 atomgit-bot 的一条内联检视线程(test/test_quint4x2_storage_dtype.py,P2:建议 NPU 用例补 hasattr 守卫)仍为未解决状态。该建议已在此前提交中采纳修复,但本人作为 fork PR 作者无目标仓库 push 权限,Web UI 与 API 均提示无权将该线程标记为解决。麻烦有权限的老师帮忙将该检视线程点「解决」,以便合并,非常感谢!

likedislike
群青世界成员
3 小时前 解决了最后一个问题
ascend-robotascend-robot成员
3 小时前 合入了pull request
ascend-robot
ascend-robot成员
3 小时前 评论:

Pull Request 已合并或已关闭。

If you want to solve this problem, you can click here to do it in the FAQs.

likedislike
AtlasAccount
AtlasAccount成员
2 小时前 评论:
流水线 pytorch_gitcode_PR_multiVersion#15241 [ commitID:f9fe42c8 ] 已完成
likedislike