Thanks for sending an requirement! Please fill in the following template to help quickly solve your problem.
RotatedBoxEncode 是旋转目标检测(Rotated Object Detection)训练阶段的核心算子。在主流旋转检测框架(如 RoI Transformer、 Oriented R-CNN、DOTA 系列检测器)中,网络需要对锚框(anchor_box)与 ground-truth 旋转框之间的几何偏差进行回归监督。RotatedBoxEncode 负责将这对旋转框的几何偏差编码为 5 通道回归 delta 目标 (dx, dy, dw, dh, dθ),供网络损失函数计算使用。它是已有 RotatedBoxDecode 算子的逆运算,两者共同构成旋转框回归的编解码闭环。
(dx, dy, dw, dh, dθ)
当前 Ascend 950(arch35)平台尚无该算子的原生 AscendC 实现,旋转检测训练管线在此平台上存在算子缺口。
NA
ln(a)−ln(b)
ln(a/b)
sin(Δθ)/(cos·cos)
tan(a)−tan(b)
约束:anchor_box / gt_box / y 三者 dtype 必须一致;anchor_box 与 gt_box shape 完全一致(无广播),秩为 3,第 1 维必须为 5;weight 若提供长度必须为 5;空 tensor(B=0 或 N=0)直接短路返回空输出。
角点形式 (x0, y0, x1, y1, θ_deg) 转中心 (cx, cy, w, h) 后逐通道编码:
(x0, y0, x1, y1, θ_deg)
(cx, cy, w, h)
w_a = max(x1_a - x0_a, 1.0), h_a = max(y1_a - y0_a, 1.0) cx_a = x0_a + w_a/2, cy_a = y0_a + h_a/2 w_g = max(x1_g - x0_g, 1.0), h_g = max(y1_g - y0_g, 1.0) cx_g = x0_g + w_g/2, cy_g = y0_g + h_g/2 dx = (cx_g - cx_a) / w_a · wx dy = (cy_g - cy_a) / h_a · wy dw = (ln(w_g) - ln(w_a)) · ww dh = (ln(h_g) - ln(h_a)) · wh dθ = (tan(θ_g) - tan(θ_a)) · wa
max(·, 1.0) 防止退化框导致除零与 log(0),并按 np.maximum 语义传播 NaN。
max(·, 1.0)
log(0)
np.maximum
rotated_box_encode_def.cpp
rotated_box_encode_graph_infer.cpp
y.dtype = anchor_box.dtype = gt_box.dtype
rotated_box_encode_infershape.cpp
y.shape = anchor_box.shape
rotated_box_encode_tiling_arch35.h/.cpp
TilingParse
Tiling
perBoxBytes=70
perBoxBytes=60
coreNum = ceil(dim0 × minDtypeBits / 32768)
ELEM_ALIGN_FACTOR=512
ubFormer = alignDown(ubSize / perBoxBytes, alignFactor)
dim0==0
coreNum=0
SetBlockDim(0)
rotated_box_encode_kernel.h
DTYPE
tilingKey
if constexpr
[5, ubStride]
ubStride = ceilAlign(boxCount, 16)
LoadAlign/StoreAlign
__simd_vf__
DxDwVF
dx
dw
DyDhVF
dy
dh
DThetaVF
dθ
dθ_prewa
wa
[B, 5, N]
N
DataCopyPad
N%16==0
N%8==0
GetValue/SetValue
GetBlockIdx
ProcessTile
blockIdx >= blockNum
dw/dh = ln(w_g/w_a)
ln(w_g) − ln(w_a)
ln(a/b)=ln(a)−ln(b)
dθ = tan(θ_g) − tan(θ_a)
sin(Δθ) / (cos(θ_g)·cos(θ_a))
dθ_prewa + 0 × dθ_prewa
inf×0=NaN
golden.py
torch.maximum
torch.log
Thanks for sending an requirement! Please fill in the following template to help quickly solve your problem.
Backgroud(背景信息)
RotatedBoxEncode 是旋转目标检测(Rotated Object Detection)训练阶段的核心算子。在主流旋转检测框架(如 RoI Transformer、 Oriented R-CNN、DOTA 系列检测器)中,网络需要对锚框(anchor_box)与 ground-truth 旋转框之间的几何偏差进行回归监督。RotatedBoxEncode 负责将这对旋转框的几何偏差编码为 5 通道回归 delta 目标
(dx, dy, dw, dh, dθ),供网络损失函数计算使用。它是已有 RotatedBoxDecode 算子的逆运算,两者共同构成旋转框回归的编解码闭环。当前 Ascend 950(arch35)平台尚无该算子的原生 AscendC 实现,旋转检测训练管线在此平台上存在算子缺口。
Origin(信息来源)
NA
Benefit / Necessity (价值/作用)
ln(a)−ln(b)替代ln(a/b)、sin(Δθ)/(cos·cos)替代tan(a)−tan(b)),规避硬件 FTZ 与奇点消去导致的精度偏差。Design(设计方案)
1. 算子接口
约束:anchor_box / gt_box / y 三者 dtype 必须一致;anchor_box 与 gt_box shape 完全一致(无广播),秩为 3,第 1 维必须为 5;weight 若提供长度必须为 5;空 tensor(B=0 或 N=0)直接短路返回空输出。
2. 计算公式
角点形式
(x0, y0, x1, y1, θ_deg)转中心(cx, cy, w, h)后逐通道编码:max(·, 1.0)防止退化框导致除零与log(0),并按np.maximum语义传播 NaN。3. Host 侧设计
rotated_box_encode_def.cpp):声明双输入/单输出/可选属性,AICore 配置 ascend950,开启动态编译静态、动态格式、动态 shape 支持。rotated_box_encode_graph_infer.cpp):y.dtype = anchor_box.dtype = gt_box.dtype,拒绝 dtype 不一致。rotated_box_encode_infershape.cpp):y.shape = anchor_box.shape,恒等映射,无广播。rotated_box_encode_tiling_arch35.h/.cpp):TilingParse解析平台信息(AIV 核数、UB 大小)。Tiling按 dtype 分两条分支:perBoxBytes=70(1 个 fp16 IO 缓冲 + 3 个 fp32 计算缓冲),UB 对齐因子 128 box,多核对齐 512 box。perBoxBytes=60(3 个 fp32 缓冲,无 Cast),UB 对齐因子 64 box,多核对齐 512 box。coreNum = ceil(dim0 × minDtypeBits / 32768),上限为平台 AIV 核数;每核 box 数对齐到ELEM_ALIGN_FACTOR=512。ubFormer = alignDown(ubSize / perBoxBytes, alignFactor);首 block / 尾 block 各自的 UB 循环数与尾块大小均预计算写入 TilingData。dim0==0时置coreNum=0、SetBlockDim(0),kernel 不执行。4. Kernel 侧设计(
rotated_box_encode_kernel.h)DTYPE模板参数(FP16=0 / FP32=1)编译期生成两个 binary,由tilingKey选择,if constexpr分支调度。[5, ubStride],ubStride = ceilAlign(boxCount, 16)保证每通道起始地址 32B 对齐(满足LoadAlign/StoreAlign要求)。__simd_vf__函数,FP32-only,双分支共享):DxDwVF:计算dx(ch0)与dw(ch2),链路 C1+C3+C4+C5+C7,峰值 5 个活跃 RegTensor。DyDhVF:计算dy(ch1)与dh(ch3),链路 C2+C3'+C4'+C6+C8,峰值 5 个活跃 RegTensor。DThetaVF:计算dθ(ch4),读取预计算的dθ_prewa乘以wa,链路 C9,峰值 3 个活跃 RegTensor。[B, 5, N]行优先,按 per-batch-segment per-channel 拆分拷贝。N对齐时走DataCopyPad快速路径(fp16 需N%16==0,fp32 需N%8==0),否则回退到标量GetValue/SetValue。GetBlockIdx→ 首/尾 block 双层循环 →ProcessTile;超配核(blockIdx >= blockNum)直接跳过。5. 数值稳定性设计
dw/dh = ln(w_g/w_a)比值下溢ln(w_g) − ln(w_a)ln(a/b)=ln(a)−ln(b)恒等变形;两操作数 ≥1.0(Maxs 下限),Ln 输入 ≥0,无非规格数dθ = tan(θ_g) − tan(θ_a)90° 奇点消去sin(Δθ) / (cos(θ_g)·cos(θ_a))dθ_prewa + 0 × dθ_prewa→ NaNinf×0=NaN恒等式;将超范围 Inf 转为 NaN,与 golden 行为对齐6. 测试与验证
golden.py),使用torch.maximum传播 NaN 语义、torch.log差值计算 dw/dh。