TAddDeqRelu¶
Tile Operation Diagram¶
Introduction¶
Fused elementwise add, dequantization scale, and ReLU clamp. Per element: dst = max(0, (src0 + src1) * deqScale) converted to half.
At the ISA level, this is a single fused instruction (TADDDEQRELU): add two int32_t source tiles, apply the floating-point dequantization scale, clamp negative results to zero, and narrow the result to half in one semantic step. Backend realization is architecture-dependent, but user-visible semantics are identical.
Math Interpretation¶
For each element (i, j) in the valid region:
The implementation uses a precision-compensated scaling sequence:
which is mathematically equivalent to x * deqScale for the add result x = src0 + src1, while avoiding precision loss for large int32_t intermediates. The final conversion to half uses saturating behavior; rounding follows round-to-nearest-even.
Assembly Syntax¶
PTO-AS form: see PTO-AS Specification.
Synchronous form:
%dst = tadddeqrelu %src0, %src1, %deqScale, %tmp : !pto.tile<...>, !pto.tile<...>, f32, !pto.tile<...>
AS Level 1 (SSA)¶
%dst = pto.tadddeqrelu %src0, %src1, %deqScale, %tmp : (!pto.tile<...>, !pto.tile<...>, f32, !pto.tile<...>) -> !pto.tile<...>
AS Level 2 (DPS)¶
pto.tadddeqrelu ins(%src0, %src1, %deqScale, %tmp : !pto.tile_buf<...>, !pto.tile_buf<...>, f32, !pto.tile_buf<...>) outs(%dst : !pto.tile_buf<...>)
C++ Intrinsic¶
Declared in include/pto/common/pto_instr.hpp:
template <typename TileDataDst, typename TileDataSrc0, typename TileDataSrc1, typename TileDataTmp,
typename... WaitEvents>
PTO_INST RecordEvent TADDDEQRELU(TileDataDst &dst, TileDataSrc0 &src0, TileDataSrc1 &src1, float deqScale,
TileDataTmp &tmp, WaitEvents &... events);
Constraints¶
- Source types:
src0andsrc1must beint32_t. - Destination type:
dstmust behalf. - Temporary type:
tmpmust beint32_t. - Layout: All tiles must be row-major (
TileData::isRowMajor). - Location: All tiles must live in
TileType::Vec. - Valid region:
validRow > 0andvalidCol > 0;src0andsrc1valid shapes must matchdstvalid shapes. - Temporary shape:
tmpmust be at least as large as the valid region ofdst. - Scale:
deqScaleis a scalarfloatapplied uniformly to every valid element. - Implementation notes (A2A3): Adds into the
int32_ttemporary tile, converts the temporary result tofloat, applies2^-17,deqScale, and2^17, performs ReLU with zero, then convertsfloattohalf. - Implementation notes (A5): Keeps intermediates in VF registers and does not need a separate UB scratch buffer internally. The public intrinsic still accepts
tmpfor interface parity with A2/A3.
Examples¶
Auto¶
#include <pto/pto-inst.hpp>
using namespace pto;
void example_auto(float deqScale) {
using SrcTileT = Tile<TileType::Vec, int32_t, 16, 16>;
using DstTileT = Tile<TileType::Vec, half, 16, 16>;
using TmpTileT = Tile<TileType::Vec, int32_t, 16, 16>;
SrcTileT src0, src1;
DstTileT dst;
TmpTileT tmp;
TADDDEQRELU(dst, src0, src1, deqScale, tmp);
}
Manual¶
#include <pto/pto-inst.hpp>
using namespace pto;
void example_manual(float deqScale) {
using SrcTileT = Tile<TileType::Vec, int32_t, 16, 16>;
using DstTileT = Tile<TileType::Vec, half, 16, 16>;
using TmpTileT = Tile<TileType::Vec, int32_t, 16, 16>;
SrcTileT src0, src1;
DstTileT dst;
TmpTileT tmp;
TASSIGN(src0, 0x0000);
TASSIGN(src1, 0x0800);
TASSIGN(tmp, 0x1000);
TASSIGN(dst, 0x1800);
TADDDEQRELU(dst, src0, src1, deqScale, tmp);
}
ASM Form Examples¶
Auto Mode¶
# Auto mode: compiler/runtime-managed placement and scheduling.
%dst = pto.tadddeqrelu %src0, %src1, %deqScale, %tmp : (!pto.tile<...>, !pto.tile<...>, f32, !pto.tile<...>) -> !pto.tile<...>
Manual Mode¶
# Manual mode: resources must be bound explicitly before issuing the instruction.
# Optional for tile operands:
# pto.tassign %arg0, @tile(0x0000)
# pto.tassign %arg1, @tile(0x0800)
# pto.tassign %tmp, @tile(0x1000)
%dst = pto.tadddeqrelu %src0, %src1, %deqScale, %tmp : (!pto.tile<...>, !pto.tile<...>, f32, !pto.tile<...>) -> !pto.tile<...>
PTO Assembly Form¶
%dst = tadddeqrelu %src0, %src1, %deqScale, %tmp : !pto.tile<...>, !pto.tile<...>, f32, !pto.tile<...>
# AS Level 2 (DPS)
pto.tadddeqrelu ins(%src0, %src1, %deqScale, %tmp : !pto.tile_buf<...>, !pto.tile_buf<...>, f32, !pto.tile_buf<...>) outs(%dst : !pto.tile_buf<...>)