CANN比赛算子总结

t1: Addcmul

t2: ClipByValue

t3: Lerp

做题与优化过程总结

1. 开发方式

在 tutorial 中发现有内置的 skills,因此我主要采用 Codex SSH 远程主机 的方式来实现代码。


2. 基础实现情况

整体来看,基础实现并不困难。

其中,第一题需要特别处理两个问题:

  1. Broadcast
  2. int8 类型及溢出模拟

我的做题顺序是:

T2 → T3 → T1

这也对应了我主观认为的题目复杂度顺序。


3. 初始优化思路

一开始,我的优化方向主要集中在:

  1. 针对不同数据范围决定开多少核;
  2. 选择合适的 tiling 大小;
  3. 研究如何进行数据切分。

我做了一天的矩阵实验,但始终没有明显优化效果。

后来我开始尝试套取实际数据范围,尤其是发现 T3 的所有测试点都小于 256KB,并且 6/7 个测试点小于 16KB。这和我原本预想的数据范围差距非常大,也改变了后续的优化方向。


4. 优化 Skill 的整理与尝试

另一个方向是参考网上已有经验,整理并 distill 出一个优化 skill。

4.1 Tiling 策略

由于大多数数据都不到 128MB,实际上每个 AI Core 中通常只需要做一次计算,因此复杂 tiling 的优化意义很小。

4.2 头尾开销优化

在头尾开销方面,比较值得优化的是:

  1. 设置合适的核数;
  2. 限制 TilingData 结构大小。

除此之外,其他方向的收益似乎并不明显。

4.3 流水编排

考虑到 AI Core 大多数情况下只需要执行一次,double buffer 在大部分情况下反而是负优化。

只有在数据较大的时候,double buffer 才可能带来一定收益。但这个收益往往小于评测机本身的波动。因此,我只在部分题目中实现了 double buffer

4.4 内存访问

在内存访问方面,我主要做了以下处理:

  1. 将 UB 使用量开到 ub_limit 的 80% 左右;
  2. GM 地址按照 512B 对齐;
  3. 尽量减少搬运次数和无效搬运。

由于数据规模较小,L2 Cache 切分没有必要。实际测试中,命中 L2 Cache 似乎也可能是负优化。

4.5 矢量计算

在矢量计算方面,Unified Buffer 内融合 是比较基础也比较必要的优化。

4.6 msProf 调试与优化

之后,我参考了一些优秀实践,用 msProf 进行实验,并 distill 了一个 msProf 调试 + 优化 skill


5. 对优化方法的反思

上述 skill 在最后的优化中帮助并不大,尤其是考虑到评测机波动等因素。

我认为真正最有用的还是:

  1. 根据实际数据范围确定核数;
  2. 根据数据范围设计 tiling 方案;
  3. 挖掘测试数据的特殊性质。

6. Tiling 方面

Tiling 的核心思路是结合实际数据范围进行设计,而不是只根据理论上的大数据场景进行优化。

由于很多测试点数据量较小,过于复杂的 tiling 反而可能带来额外开销。因此,tiling 策略应尽量保持简单,并减少无效切分。


7. 核数选择

核数方面,我采用了:

  1. 本地矩阵实验;
  2. OJ 提交测试。

本地测试环境是 A3,和云端芯片并不完全一致,再加上一些其他因素,本地实验结果和云端结果很难完全对应。

因此,最终还是以 OJ 上的直接提交结果 更为权威。


8. 特殊数据性质挖掘

在 T1 中,我全面实现了 broadcast。随后通过分析特殊数据,发现了一些重要性质:

  1. dimensions <= 5
  2. 大部分数据不会进入 broadcast 分支;
  3. 只有两个测试点需要实现 int8;
  4. 其中一个 int8 测试点还需要模拟 int8 溢出。

根据这些性质,我最终舍弃了其中一个测试点,但优化了 shape 判断和 tiling 结构,取得了比较高的收益。


9. 最后的调参方式

后期开始进行数据拟合,主要通过直觉调整核数。

一般来说,我会在本地实验结果的基础上,把核数往更大的方向调一些,然后多次提交 OJ,寻找评测效果较好的配置。


总结

整体来看,这次优化中最重要的经验是:

不要一开始就陷入通用优化模板,而是要先弄清楚真实数据范围和测试点特征。

在数据量较小、评测波动明显的情况下,复杂的流水、L2 Cache 切分、double buffer 等优化不一定有效,甚至可能带来负收益。

最终真正有效的优化主要来自:

  1. 数据范围分析;
  2. 核数选择;
  3. tiling 结构简化;
  4. 特殊测试点性质挖掘;
  5. 多次 OJ 提交拟合评测结果。

最后拿下 rk1,可能是参加的人比较少吧。