数据流调度策略:输入驻留、权值驻留、输出驻留

各位同学,今天我们来聊聊卷积加速器里最核心的一个话题——数据流调度策略。说白了,就是数据怎么在计算阵列里流动。我做了这么多年芯片,见过太多团队在架构设计时忽略了这一点,结果流片回来性能死活上不去。嗯,今天咱们就把这块彻底讲透。

为什么数据流调度这么重要?

你想想看,卷积运算的本质是什么?就是一堆乘加操作。但真正限制性能的,从来不是计算单元够不够快,而是数据能不能喂得进去。我遇到过最夸张的一个项目,PE阵列利用率连30%都不到,查到最后发现是数据搬运把带宽吃死了。

数据流调度策略,就是决定谁在计算阵列里“待着不动”,谁在“来回跑”。常见的三种策略:

  • 输入驻留(Input Stationary, IS):输入特征图待在PE里不动
  • 权值驻留(Weight Stationary, WS):权值待在PE里不动
  • 输出驻留(Output Stationary, OS):部分和待在PE里不动

这三种策略各有各的脾气,选错了,性能直接腰斩。

输入驻留(IS)—— 适合小batch的场景

输入驻留,就是把输入特征图的数据固定在PE里。权值在阵列里广播,部分和沿着某个方向累加。

我个人的习惯是,在做移动端推理芯片时,优先考虑IS。为什么?因为移动端的batch size通常很小,甚至batch=1。这时候输入数据复用性高,权值反而需要频繁更新。

核心特点:

  • 输入数据只在加载时搬一次,后续不动
  • 权值在PE阵列里广播,每个PE拿到的权值不同
  • 部分和沿着列方向累加

举个例子,假设你有一个3x3的卷积核,输入是32x32的特征图。用IS策略,每个PE负责一个输入像素位置,权值轮流广播过来。这样输入数据只从DRAM读一次,省了不少带宽。

适用场景:

  • batch size较小(1~4)
  • 输入特征图尺寸较大,权值相对较小
  • 带宽受限,但计算资源充裕

我曾经踩过的坑:有一次做视频处理芯片,想当然用了IS策略。结果视频流是连续帧,每帧的输入数据完全不同,IS的输入复用优势完全发挥不出来。后来改成WS,性能直接翻倍。所以一定要看你的数据特点。

权值驻留(WS)—— 大batch的王者

权值驻留,顾名思义,权值数据待在PE里不动。输入特征图广播,部分和累加。

说白了,WS就是让权值“躺平”,输入数据“跑起来”。这在训练芯片里特别常见,因为训练时通常batch size很大,同一个权值要跟很多个输入做卷积。

核心特点:

  • 权值只加载一次,后续复用
  • 输入特征图在阵列里广播
  • 每个PE独立计算部分和

我记得有一次做云端推理芯片,客户要求支持batch=64。我二话不说选了WS策略。为什么?因为权值复用率能达到64倍,输入数据虽然广播开销大,但权值搬运的带宽省下来了。整体算下来,能效比IS高了40%。

适用场景:

  • batch size较大(8以上)
  • 权值数量远小于输入数据量
  • 权值可以提前预加载到PE的本地寄存器

小技巧:WS策略下,权值可以提前从DRAM搬到PE的本地SRAM里。我建议在计算开始前,先花几个周期把权值全部加载好。这样计算阶段就不会有等待权值的情况,流水线跑得特别顺。

输出驻留(OS)—— 减少部分和搬运

输出驻留,是把部分和(partial sum)留在PE里累加。输入和权值都广播进来,每个PE负责一个输出像素位置的部分和累加。

这个策略我用的相对少一些,但在某些场景下特别好使。比如做深度可分离卷积(depthwise convolution)时,每个输出通道只跟一个输入通道相关,部分和的累加次数很少,OS策略能省掉大量部分和搬运。

核心特点:

  • 部分和留在PE里,直到累加完成
  • 输入和权值都广播
  • 每个PE对应一个输出像素位置

适用场景:

  • 输出通道数较少
  • 卷积核尺寸较大,需要多次累加
  • 部分和位宽较大,搬运成本高

注意:OS策略下,PE的本地存储要能放下完整的部分和。我曾经有个项目,部分和位宽32bit,输出特征图256x256,一个PE要存256个部分和,本地寄存器根本不够用。后来改成混合策略才解决。

三种策略的对比

咱们直接上表格,一目了然:

对比维度 输入驻留(IS) 权值驻留(WS) 输出驻留(OS)
谁不动 输入特征图 权值 部分和
谁广播 权值 输入特征图 输入+权值
数据复用性 输入复用高 权值复用高 部分和复用高
适合batch 小batch(1~4) 大batch(8+) 中等batch
存储需求 PE存输入 PE存权值 PE存部分和
典型应用 移动端推理 云端训练/推理 深度可分离卷积

实际项目中的选择思路

说实话,没有一种策略是万能的。我个人的经验是,先看你的数据特点:

  1. 先看batch size:batch大选WS,batch小选IS
  2. 再看卷积类型:depthwise卷积优先考虑OS
  3. 最后看带宽瓶颈:如果DRAM带宽是瓶颈,选能减少数据搬运的策略

你想想看,如果batch=1还硬要用WS,权值只复用一次,但输入数据要广播到所有PE,带宽浪费得一塌糊涂。反过来,batch=64用IS,输入数据只复用一次,权值却要反复加载,也是得不偿失。

我的建议:做架构设计时,先画一个数据流图。把输入、权值、部分和三条数据路径画清楚,看看哪条路径的带宽压力最大。然后选一个能缓解这个瓶颈的策略。如果还是拿不准,就做RTL仿真,跑几个典型case看看实际吞吐量。

知识体系总览

下面这张图,是我自己总结的数据流调度策略选择逻辑,你们可以保存下来参考:

数据流调度策略选择逻辑 卷积加速器数据流 batch size? 小batch (1~4) 大batch (8+) 输入驻留 (IS) 权值驻留 (WS) depthwise? 带宽瓶颈? 是 OS 否 否 确认最终策略 RTL仿真验证 跑典型case,确认吞吐量达标

嗯,这张图把选择逻辑串起来了。从batch size入手,再根据卷积类型和带宽瓶颈做二次判断。记住,没有正确的策略,只有最适合你场景的策略。

避坑指南

最后分享几个我亲身踩过的坑:

  • 我曾经以为IS一定比WS好,因为输入复用率高。结果在batch=32的场景下,权值搬运成了瓶颈,WS反而更优。所以别凭感觉选,拿数据说话。
  • 我曾经在OS策略下没算好部分和位宽,导致累加溢出。后来在PE里加了饱和截位逻辑才解决。做OS一定要提前算好部分和的最大位宽。
  • 混合策略其实更常见。很多商用芯片不是纯IS或纯WS,而是分层混合。比如第一层用IS,第二层用WS。这个我们后面章节会详细讲。

好了,数据流调度策略的核心内容就这些。记住,选策略之前,先搞清楚你的数据长什么样。下一节我们聊聊具体的PE微架构设计,到时候会用到今天讲的知识。

可可精品资料库