已合并
add setdeqscalel4 #46
li_zeran创建于 2025年12月23日
add setdeqscalel4 #46
已合并
li_zeran创建于 2025年12月23日
14 个文件变更+161-12
Mdocs/python-api/language/generated/asc.language.basic.set_deq_scale.md+19-0
@@ -4,6 +4,8 @@
4 4 
5### asc.language.basic.set_deq_scale(scale: float, offset: int, sign_mode: bool) → None5### asc.language.basic.set_deq_scale(scale: float, offset: int, sign_mode: bool) → None
6 6 
7+### asc.language.basic.set_deq_scale(vdeq: LocalTensor, vdeq_info: VdeqInfo) -> None:
8+ 
7设置DEQSCALE寄存器的值。9设置DEQSCALE寄存器的值。
8 10 
9**对应的Ascend C函数原型**11**对应的Ascend C函数原型**
@@ -12,6 +14,9 @@
12__aicore__ inline void SetDeqScale(half scale)14__aicore__ inline void SetDeqScale(half scale)
13 15 
14__aicore__ inline void SetDeqScale(float scale, int16_t offset, bool signMode)16__aicore__ inline void SetDeqScale(float scale, int16_t offset, bool signMode)
17+ 
18+template <typename T>
19+__aicore__ inline void SetDeqScale(const LocalTensor<T>& vdeq, const VdeqInfo& vdeqInfo)
15```20```
16 21 
17**参数说明**22**参数说明**
@@ -20,6 +25,8 @@ __aicore__ inline void SetDeqScale(float scale, int16_t offset, bool signMode)
20- scale(float):scale量化参数,float类型。25- scale(float):scale量化参数,float类型。
21- offset:offset量化参数,int16_t类型,只有前9位有效。26- offset:offset量化参数,int16_t类型,只有前9位有效。
22- sign_mode:bool类型,表示量化结果是否带符号。27- sign_mode:bool类型,表示量化结果是否带符号。
28+- vdeq: 输入量化tensor,大小为128Byte。类型为LocalTensor,支持的TPosition为VECIN/VECCALC/VECOUT。LocalTensor的起始地址需要32字节对齐。
29+- vdeq_info: 存储量化tensor信息的数据结构,结构体内包含量化tensor中的16组量化参数。
23 30 
24**调用示例**31**调用示例**
25 32 
@@ -28,6 +35,8 @@ __aicore__ inline void SetDeqScale(float scale, int16_t offset, bool signMode)
28scale = 1.035scale = 1.0
29asc.set_deq_scale(scale)36asc.set_deq_scale(scale)
30asc.cast(cast_dst_local, cast_dsrc_local, asc.RoundMode.CAST_NONE, src_size)37asc.cast(cast_dst_local, cast_dsrc_local, asc.RoundMode.CAST_NONE, src_size)
38+```
39+```python
31# CastDeq40# CastDeq
32scale = 1.041scale = 1.0
33offset = 042offset = 0
@@ -35,3 +44,13 @@ sign_mode = True
35asc.set_deq_scale(scale, offset, sign_mode)44asc.set_deq_scale(scale, offset, sign_mode)
36asc.cast_deq(dst_local, src_local, count=src_size, is_vec_deq=False, half_block=False)45asc.cast_deq(dst_local, src_local, count=src_size, is_vec_deq=False, half_block=False)
37```46```
47+```python
48+# CastVdeq
K
Kkong08081月9日

调用示例 建议隔开一些,或者分三个更清晰

likedislike
49+vdeq_local = asc.LocalTensor(dtype=asc.uint64, pos=asc.TPosition.VECIN, addr=0, tile_size=16)
50+vdeq_scale = [1.0] * 16
51+vdeq_offset = [0] * 16
52+vdeq_sign_mode = [False] * 16
53+vdeq_info = asc.VdeqInfo(vdeq_scale, vdeq_offset, vdeq_sign_mode)
54+asc.set_deq_scale(vdeq_local, vdeq_info)
55+asc.cast_deq(dst_local, src_local, count=src_size, is_vec_deq=True, half_block=False)
56+```
Minclude/ascir/API/Types.td+5-0
@@ -438,4 +438,9 @@ def UnaryRepeatParams : APIType<"UnaryRepeatParams"> {
438 let mnemonic = "unary_repeat_params";438 let mnemonic = "unary_repeat_params";
439 let apiName = "AscendC::UnaryRepeatParams";439 let apiName = "AscendC::UnaryRepeatParams";
440}440}
441+ 
442+def VdeqInfo : APIType<"VdeqInfo"> {
443+ let mnemonic = "vdeq_info";
444+ let apiName = "AscendC::VdeqInfo";
445+}
441#endif // API_TYPES_TD446#endif // API_TYPES_TD
Minclude/ascir/Dialect/Asc/IR/Basic/OpVecVconv.td+6-0
@@ -70,6 +70,12 @@ def AscendC_SetDeqScaleOp : APIOp<"set_deq_scale", "SetDeqScale", [AttrSizedOper
70 }];70 }];
71}71}
72 72 
73+def AscendC_SetDeqScaleL4Op : VectorOp<"set_deq_scale_l4", "SetDeqScale"> {
74+ let description = "Set dequantization scale, offset and sign mode information";
75+ let arguments = (ins AscendC_LocalTensor:$vdeq, AscendC_VdeqInfo:$vdeqInfo
76+ );
77+}
78+ 
73defm AddReluCast : BinaryCastL012Op<"add_relu_cast", "AddReluCast">;79defm AddReluCast : BinaryCastL012Op<"add_relu_cast", "AddReluCast">;
74defm SubReluCast : BinaryCastL012Op<"sub_relu_cast", "SubReluCast">;80defm SubReluCast : BinaryCastL012Op<"sub_relu_cast", "SubReluCast">;
75 81 
Minclude/ascir/Dialect/Asc/IR/Interfaces.td+2-0
@@ -47,6 +47,8 @@ class AscendC_InterfaceMethods {
47 "getIsExhaustedSuspension", "bool">;47 "getIsExhaustedSuspension", "bool">;
48 InterfaceMethod getIsFullSort = GetMethod<"isFullSort", 48 InterfaceMethod getIsFullSort = GetMethod<"isFullSort",
49 "getIsFullSort", "bool">;49 "getIsFullSort", "bool">;
50+ InterfaceMethod getVdeq = GetMethod<"vdeq", "getVdeq">;
51+ InterfaceMethod getVdeqInfo = GetMethod<"vdeqInfo", "getVdeqInfo">;
50}52}
51 53 
52class AscendC_OpInterface<string name, list<Interface> baseInterfaces = []>54class AscendC_OpInterface<string name, list<Interface> baseInterfaces = []>
Minclude/ascir/Target/Asc/Basic/VecVconv.h+1-0
@@ -76,6 +76,7 @@ LogicalResult printOperation(CodeEmitter &emitter, ascendc::CastDeqL2Op op);
76 76 
77LogicalResult printOperation(CodeEmitter &emitter, ascendc::SetDeqScaleOp op);77LogicalResult printOperation(CodeEmitter &emitter, ascendc::SetDeqScaleOp op);
78 78 
79+LogicalResult printOperation(CodeEmitter& emitter, ascendc::SetDeqScaleL4Op op);
79} // namespace ascendc80} // namespace ascendc
80} // namespace mlir81} // namespace mlir
81 82 
Mlib/Target/AscendC/Basic/VecVconv.cpp+9-0
@@ -86,3 +86,12 @@ LogicalResult mlir::ascendc::printOperation(CodeEmitter &emitter, ascendc::CastD
86 printUnaryL2Params(emitter, op);86 printUnaryL2Params(emitter, op);
87 return success();87 return success();
88}88}
89+ 
90+LogicalResult mlir::ascendc::printOperation(CodeEmitter &emitter, ascendc::SetDeqScaleL4Op op) {
91+ auto &os = emitter.ostream();
92+ os << ascNamespace << "::" << op.getAPIName() << "("
93+ << emitter.getOrCreateName(op.getVdeq()) << ", "
94+ << emitter.getOrCreateName(op.getVdeqInfo()) << ")";
95+
96+ return success();
97+}
Mlib/Target/AscendC/Translation.cpp+1-1
@@ -215,7 +215,7 @@ using PrintableOpTypes = std::tuple<
215 ascendc::RsqrtL2Op, ascendc::SqrtL2Op, ascendc::NegL2Op,215 ascendc::RsqrtL2Op, ascendc::SqrtL2Op, ascendc::NegL2Op,
216 // VecVcon (Type conversion) operations216 // VecVcon (Type conversion) operations
217 ascendc::CastL0Op, ascendc::CastL1Op, ascendc::CastL2Op, ascendc::CastDeqL0Op, ascendc::CastDeqL1Op,217 ascendc::CastL0Op, ascendc::CastL1Op, ascendc::CastL2Op, ascendc::CastDeqL0Op, ascendc::CastDeqL1Op,
218- ascendc::CastDeqL2Op,218+ ascendc::CastDeqL2Op, ascendc::SetDeqScaleL4Op,
219 // Vector gatherMask operations219 // Vector gatherMask operations
220 ascendc::GatherMaskOp, ascendc::GetGatherMaskRemainCountOp,220 ascendc::GatherMaskOp, ascendc::GetGatherMaskRemainCountOp,
221 221 
Mpython/asc/language/__init__.py+1-0
@@ -275,6 +275,7 @@ from .core.types import (
275 LoadData3DParamsV2Pro,275 LoadData3DParamsV2Pro,
276 LoadDataRepeatParam,276 LoadDataRepeatParam,
277 get_shape_size,277 get_shape_size,
278+ VdeqInfo,
278)279)
279from .core.aipp_types import (280from .core.aipp_types import (
280 AippParams,281 AippParams,
Mpython/asc/language/basic/utils.py+12-0
@@ -3557,6 +3557,8 @@ def set_deq_scale_docstring():
3557 3557 
3558 __aicore__ inline void SetDeqScale(float scale, int16_t offset, bool signMode)3558 __aicore__ inline void SetDeqScale(float scale, int16_t offset, bool signMode)
3559 3559 
3560+ template <typename T>
3561+ __aicore__ inline void SetDeqScale(const LocalTensor<T>& vdeq, const VdeqInfo& vdeqInfo)
3560 """3562 """
3561 3563 
3562 param_list = """3564 param_list = """
@@ -3566,6 +3568,8 @@ def set_deq_scale_docstring():
3566 - scale(float):scale量化参数,float类型。3568 - scale(float):scale量化参数,float类型。
3567 - offset:offset量化参数,int16_t类型,只有前9位有效。3569 - offset:offset量化参数,int16_t类型,只有前9位有效。
3568 - sign_mode:bool类型,表示量化结果是否带符号。3570 - sign_mode:bool类型,表示量化结果是否带符号。
3571+ - vdeq: 输入量化tensor,大小为128Byte。类型为LocalTensor,支持的TPosition为VECIN/VECCALC/VECOUT。LocalTensor的起始地址需要32字节对齐。
3572+ - vdeqInfo: 存储量化tensor信息的数据结构,结构体内包含量化tensor中的16组量化参数。
3569 """3573 """
3570 3574 
3571 py_example = """3575 py_example = """
@@ -3583,6 +3587,14 @@ def set_deq_scale_docstring():
3583 sign_mode = True3587 sign_mode = True
3584 asc.set_deq_scale(scale, offset, sign_mode)3588 asc.set_deq_scale(scale, offset, sign_mode)
3585 asc.cast_deq(dst_local, src_local, count=src_size, is_vec_deq=False, half_block=False)3589 asc.cast_deq(dst_local, src_local, count=src_size, is_vec_deq=False, half_block=False)
3590+ # CastVdeq
3591+ vdeq_local = asc.LocalTensor(dtype=asc.uint64, pos=asc.TPosition.VECIN, addr=0, tile_size=16)
3592+ vdeq_scale = [1.0] * 16
3593+ vdeq_offset = [0] * 16
3594+ vdeq_sign_mode = [False] * 16
3595+ vdeq_info = asc.VdeqInfo(vdeq_scale, vdeq_offset, vdeq_sign_mode)
3596+ asc.set_deq_scale(vdeq_local, vdeq_info)
3597+ asc.cast_deq(dst_local, src_local, count=src_size, is_vec_deq=True, half_block=False)
3586 """3598 """
3587 3599 
3588 return [func_introduction, cpp_signature, param_list, "", "", py_example]3600 return [func_introduction, cpp_signature, param_list, "", "", py_example]
Mpython/asc/language/basic/vec_vconv.py+23-9
@@ -6,7 +6,7 @@
6# INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE.6# INCLUDING BUT NOT LIMITED TO NON-INFRINGEMENT, MERCHANTABILITY, OR FITNESS FOR A PARTICULAR PURPOSE.
7# See LICENSE in the root of the software repository for the full text of the License.7# See LICENSE in the root of the software repository for the full text of the License.
8 8 
9-from typing import List, overload, Optional9+from typing import List, overload
10 10 
11from ..._C import ir11from ..._C import ir
12from ..core.dtype import KnownTypes, KnownTypes as KT12from ..core.dtype import KnownTypes, KnownTypes as KT
@@ -14,7 +14,7 @@ from ..core.enums import RoundMode
14from ..core.ir_value import RuntimeBool, RuntimeInt, RuntimeFloat, materialize_ir_value as _mat14from ..core.ir_value import RuntimeBool, RuntimeInt, RuntimeFloat, materialize_ir_value as _mat
15from ..core.tensor import LocalTensor15from ..core.tensor import LocalTensor
16from ..core.utils import require_jit, global_builder, DefaultValued, OverloadDispatcher16from ..core.utils import require_jit, global_builder, DefaultValued, OverloadDispatcher
17-from ..core.types import BinaryRepeatParams, UnaryRepeatParams17+from ..core.types import BinaryRepeatParams, UnaryRepeatParams, VdeqInfo
18from .utils import op_impl, set_binary_docstring, set_common_docstring18from .utils import op_impl, set_binary_docstring, set_common_docstring
19from .vec_unary import op_impl as unary_op_impl19from .vec_unary import op_impl as unary_op_impl
20 20 
@@ -125,15 +125,29 @@ def set_deq_scale(scale: float, offset: int, sign_mode: bool) -> None:
125 ...125 ...
126 126 
127 127 
128+@overload
129+def set_deq_scale(vdeq: LocalTensor, vdeq_info: VdeqInfo) -> None:
130+ ...
131+ 
132+ 
128@require_jit133@require_jit
129@set_common_docstring(api_name="set_deq_scale")134@set_common_docstring(api_name="set_deq_scale")
130-def set_deq_scale(scale: RuntimeFloat, offset: Optional[RuntimeInt] = None, 135+def set_deq_scale(*args, **kwargs) -> None:
131- sign_mode: Optional[RuntimeBool] = None) -> None:136+ builder = global_builder.get_ir_builder()
132- if offset is None and sign_mode is None:137+ dispatcher = OverloadDispatcher("set_deq_scale")
133- global_builder.get_ir_builder().create_asc_SetDeqScaleOp(_mat(scale, KnownTypes.half).to_ir())138+ @dispatcher.register(vdeq=LocalTensor, vdeq_info=VdeqInfo)
134- else:139+ def _(vdeq: LocalTensor, vdeq_info: VdeqInfo):
135- global_builder.get_ir_builder().create_asc_SetDeqScaleOp(_mat(scale, KnownTypes.float32).to_ir(), \140+ builder.create_asc_SetDeqScaleL4Op(vdeq.to_ir(), vdeq_info.to_ir())
136- _mat(offset, KnownTypes.int16).to_ir(), _mat(sign_mode, KnownTypes.bit).to_ir())141+ @dispatcher.register(scale=RuntimeFloat)
142+ def _(scale: RuntimeFloat):
143+ builder.create_asc_SetDeqScaleOp(_mat(scale, KnownTypes.half).to_ir())
144+ @dispatcher.register(scale=RuntimeFloat, offset=RuntimeInt, sign_mode=RuntimeBool)
145+ def _(scale: RuntimeFloat, offset: RuntimeInt, sign_mode: RuntimeBool):
146+ builder.create_asc_SetDeqScaleOp(_mat(scale, KnownTypes.float32).to_ir(),
147+ _mat(offset, KnownTypes.int16).to_ir(),
148+ _mat(sign_mode, KnownTypes.bit).to_ir())
149+ dispatcher(*args, **kwargs)
150+ 
137 151 
138 152 
139@overload153@overload
Mpython/asc/language/core/__init__.py+3-1
@@ -114,7 +114,8 @@ from .types import (
114 LoadData3DParamsV2,114 LoadData3DParamsV2,
115 LoadData3DParamsV2Pro,115 LoadData3DParamsV2Pro,
116 LoadDataRepeatParam,116 LoadDataRepeatParam,
117- get_shape_size117+ get_shape_size,
118+ VdeqInfo,
118)119)
119from .utils import ceildiv, static_assert120from .utils import ceildiv, static_assert
120 121 
@@ -236,6 +237,7 @@ __all__ = [
236 "LoadData3DParamsV2Pro",237 "LoadData3DParamsV2Pro",
237 "LoadDataRepeatParam",238 "LoadDataRepeatParam",
238 "get_shape_size",239 "get_shape_size",
240+ "VdeqInfo",
239 # .core.utils241 # .core.utils
240 "ceildiv",242 "ceildiv",
241 "static_assert",243 "static_assert",
Mpython/asc/language/core/types.py+64-0
@@ -1915,3 +1915,67 @@ class FixpipeParamsV220(IRValue):
1915 def to_ir(self) -> IRHandle:1915 def to_ir(self) -> IRHandle:
1916 return self.handle1916 return self.handle
1917 1917 
1918+ 
1919+class VdeqInfo(IRValue):
1920+ 
1921+ @overload
1922+ def __init__(
1923+ self,
1924+ scale: List[float],
1925+ offset: List[int],
1926+ sign_mode: List[bool],
1927+ ) -> None:
1928+ 
1929+ ...
1930+ 
1931+ @overload
1932+ def __init__(self, handle: IRHandle) -> None:
1933+ """This contructor should not be called by user"""
1934+ ...
1935+ 
1936+ 
1937+ @require_jit
1938+ def __init__(
1939+ self,
1940+ scale: Optional[List[float]] = None,
1941+ offset: Optional[List[int]] = None,
1942+ sign_mode: Optional[List[bool]] = None,
1943+ handle: Optional[IRHandle] = None,
1944+ ) -> None:
1945+ if handle is not None:
1946+ self.handle = handle
1947+ return
1948+ 
1949+ if scale is None or offset is None or sign_mode is None:
1950+ raise ValueError("VdeqInfo requires scale / offset / sign_mode")
1951+ if len(scale) != 16 or len(offset) != 16 or len(sign_mode) != 16:
1952+ raise ValueError("VdeqInfo expects exactly 16 elements per field")
1953+ 
1954+ builder = global_builder.get_ir_builder()
1955+ 
1956+ from .array import array
1957+
1958+ scale_array = array(KnownTypes.float32, scale)
1959+ offset_array = array(KnownTypes.int16, offset)
1960+ sign_mode_array = array(KnownTypes.bit, [1 if x else 0 for x in sign_mode])
1961+ 
1962+ self.handle = builder.create_asc_ConstructOp(
1963+ builder.get_asc_VdeqInfoType(),
1964+ [
1965+ scale_array.to_ir(),
1966+ offset_array.to_ir(),
1967+ sign_mode_array.to_ir(),
1968+ ],
1969+ builder.get_type_array_attr([
1970+ scale_array.to_ir().get_type(),
1971+ offset_array.to_ir().get_type(),
1972+ sign_mode_array.to_ir().get_type(),
1973+ ]),
1974+ )
1975+ 
1976+ @classmethod
1977+ def from_ir(cls, handle: IRHandle) -> "VdeqInfo":
1978+ return cls(handle=handle)
1979+ 
1980+ def to_ir(self) -> IRHandle:
1981+ return self.handle
Mpython/test/unit/language/basic/test_common_api.py+6-1
@@ -576,7 +576,12 @@ def test_set_deq_scale(mock_launcher_run):
576 def kernel_set_deq_scale() -> None:576 def kernel_set_deq_scale() -> None:
577 asc.set_deq_scale(1.0)577 asc.set_deq_scale(1.0)
578 asc.set_deq_scale(1.0, 5, False)578 asc.set_deq_scale(1.0, 5, False)
579- 579+ vdeq_local = asc.LocalTensor(dtype=asc.uint64, pos=asc.TPosition.VECIN, addr=0, tile_size=16)
580+ vdeq_scale = [1.0] * 16
581+ vdeq_offset = [5] * 16
582+ vdeq_sign_mode = [False] * 16
583+ vdeq_info = asc.VdeqInfo(vdeq_scale, vdeq_offset, vdeq_sign_mode)
584+ asc.set_deq_scale(vdeq_local, vdeq_info)
580 kernel_set_deq_scale[1]()585 kernel_set_deq_scale[1]()
581 assert mock_launcher_run.call_count == 1586 assert mock_launcher_run.call_count == 1
582 587 
Mtest/Target/AscendC/basic/vec_vconv.mlir+9-0
@@ -70,6 +70,15 @@ func.func @emit_set_deq_scale(%arg0: f16, %arg1: f32, %arg2: i16) {
70 return70 return
71}71}
72 72 
73+// CHECK-LABEL:void emit_set_deq_scale_l4(AscendC::LocalTensor<float> v1, AscendC::VdeqInfo v2) {
74+// CHECK-NEXT: AscendC::SetDeqScale(v1, v2);
75+// CHECK-NEXT: return;
76+// CHECK-NEXT: }
77+func.func @emit_set_deq_scale_l4(%vdeq: !ascendc.local_tensor<32xf32>, %vdeq_info: !ascendc.vdeq_info) {
78+ ascendc.set_deq_scale_l4 %vdeq, %vdeq_info : !ascendc.local_tensor<32xf32>, !ascendc.vdeq_info
79+ return
80+}
81+ 
73// CHECK-LABEL:void emit_cast_deq(AscendC::LocalTensor<float> v1, AscendC::LocalTensor<float> v2, uint8_t v3, AscendC::UnaryRepeatParams v4, uint64_t v5, uint64_t v6, int32_t v7) {82// CHECK-LABEL:void emit_cast_deq(AscendC::LocalTensor<float> v1, AscendC::LocalTensor<float> v2, uint8_t v3, AscendC::UnaryRepeatParams v4, uint64_t v5, uint64_t v6, int32_t v7) {
74// CHECK-NEXT: AscendC::CastDeq<float, float, 0, 0>(v1, v2, v7);83// CHECK-NEXT: AscendC::CastDeq<float, float, 0, 0>(v1, v2, v7);
75// CHECK-NEXT: AscendC::CastDeq<float, float, 1, 0, 0>(v1, v2, v5, v3, v4);84// CHECK-NEXT: AscendC::CastDeq<float, float, 1, 0, 0>(v1, v2, v5, v3, v4);