Juggling Pipeline 动态重构流水线

近一段时间FPGA因为其优越的计算性能和低功耗而备受关注,成为GPU之外硬件计算加速的新选择。除了目前FPGA已经广泛应用的通信领域,许多公司也开始使用FPGA进行CNN神经网络的加速计算。这篇博客提出一种基于FPGA动态可重构技术的新型流水线设计,以提高CNN神经网络的加速效率。

1 背景

1.1 FPGA 资源不足的问题

算法计算单元,使用FPGA进行计算加速时,时常会面临资源不足的问题,从而导致部署上的困难。如ICLR2016最佳论文,深鉴科技韩松团队的CNN神经网络深度剪枝和压缩算法,对目前主流且比较大的VGG,AlexNet等网络进行了大幅度压缩,将参数降低到了原来的二十分之一甚至更多,从而更加轻松地在FPGA上部署。


如图所示,FPGA板上资源分为系统静态电路(包含PCIe接口,DDR控制器等)和用户电路两部分。将一个包含六层的神经网络部署在用户电路上时,出现资源不足的问题。


但是韩松团队的深度压缩算法本质上是一种网络优化算法,而不是普适性的部署策略。其在FPGA2017最佳论文,即是使用优化AlexNet类似的方法,对ResNet进行了压缩,并应用在声音处理上,针对ResNet采用了许多不同的压缩算法。

1.2 现有的部署方案

到目前为止,能够解决资源不足问题的,适用于FPGA的普适性部署策略主要有两种:分布式计算方案,传统的重构计算方案。分布式计算方案直接使用多块FPGA板卡,分布在多个服务器上,使用局域网进行通信;或集中在一个服务器上,由一个CPU进行调度,使用PCIe总线进行通信。从而实现计算单元的完整部署,以及完全的流水线计算。传统重构计算方案,仍然使用一块FPGA板卡,通过反复重构用户电路,实现资源的复用。


仍然以前图的六层神经网络为例,左图为分布式计算方案,将前三层和后三层分别部署在两个包含FPGA板卡和主控CPU的服务器上,两台服务器之间通过局域网进行通信。右图为传统重构方案,使用一块FPGA板卡,首先将前三层部署在FPGA上,计算完成后,将后三层重构在FPGA上,实现完整的计算。


通常情况下,分布式计算方案具有更强的可行性,也是目前较为普遍的解决方案。微软在2014年发表的Catapult for brevity计算中心解决方案中,就使用了一个由48个FPGA服务器构成的小集群中,实现了一个包含8个流水级的bing搜索rank加速方案。假设不同部署方案的硬件计算性能一致,分布式计算主要有以下几个特点:

  • 实现完全流水线计算,实现极限吞吐率。
  • 需要多个FPGA计算节点,无法在单个FPGA上部署(即仅适用于服务器计算,而不适用于手机等终端计算)。
  • 局域网的带宽限制造成延时,可能成为计算瓶颈,抵消FPGA加速带来的收益。

实际上一个设计优良的分布式计算方案,可能能够解决延时问题,但不进行资源复用的解决方案,无法在单个FPGA上部署,不适用于手机等终端的计算。而传统的重构计算方案尽管能够在单个FPGA上部署,但有着显而易见的缺点:

  • 无法实现流水线计算,吞吐率低。
  • 重构FPGA造成延时。

传统的重构计算方案可以通过每次重构进行更多数据的计算来提高吞吐率,但这样会造成巨大的延时。如果追求低延时,则会造成吞吐率的低下,同时FPGA重构的时间要长于GPU(约为1ms / 10ms量级),延时仍然无法避免。

2 Juggling Pipeline

2.1 部署方案说明

Juggling Pipeline 是基于 FPGA 部分重构技术实现的,是一种资源复用的流水线计算方案。其可以仅使用一块 FPGA 实现较大的计算单元的部署,能够实现极低的延时,同时实现在一块 FPGA 板卡下最大的吞吐率。


仍以前图六层神经网络为例,一块 FPGA 板卡上最多可以部署三层。如图所示,将 FPGA 划分为三个区域,始终有且仅有一个区域处于重构状态(灰色区域),剩余区域处于计算状态(白色区域)。最左边 Stage1 时(略去了 Stage0),Data0 正在计算 Layer1,Data1 正在计算 Layer0;最右边 Stage6 时,Data0 已经在 Stage5 计算完毕并输出,Data1 正在计算 Layer5,Data2 进入 FPGA 正在计算 Layer0;重构状态依次遍历 FPGA 上所有区域,从而达到资源的复用和流水线的推进。


实际上,该方案以 FPGA 上一个区域的资源作为代价(即始终有一个区域的资源没有进行计算),在一块 FPGA 上实现了不完全流水线。该方案将重构视为每次进入 FPGA 的一组数据的哨兵数据,以抵消 FPGA 重构带来的延时。

假设计算过程可均分为 N 个流水级,片上可以容纳 S 个流水级,共需要处理的数据量为 D,每个流水级的处理时间为 t。处理全部数据需要的时间为:

T_total = [ S - 2 + N / ( S - 1 ) × D ] × t

假设 D 远大于 S,那么平均处理一个数据需要的时间为:

T = N / ( S - 1 ) × t

不考虑分布式计算方案和该方案中数据通信和同步的时间,那么两个方案都达到相同的极限延时,所以根据上式的计算结果,Juggling Pipeline 比完全流水线(即本方案比分布式计算方案)吞吐率相差 N / ( S - 1 )。直观上理解也就是本方案在任一时刻有 S - 1 层在工作,而分布式计算方案有 N 在工作,故而产生吞吐率的差距。在 S 较大的情况下(后文中的 SqueezeNet 案例中,S为10),不处于计算的区域产生的影响基本可忽略,本方案实际上以极小的代价得到了最好的吞吐率和延时。


如上图所示,为流水线的示意图,横向表示时间的流逝,可以看到在任一时刻,始终有两层处于工作状态,与完全流水线相比,吞吐量的差距为 6 / ( 3 -1 ) = 3。


在真实情况下,分布式计算方案因为延时的原因,与本方案的吞吐量差距可能会变小。但是由于本方案使用了 FPGA 可重构技术,划定多个可重构区域时可能出现的 timing 和 DRC 错误。各流水级对 LUT、BRAM、DSP 等资源不均匀的的使用,造成一定程度的资源浪费。同时也大大提高了电路设计流程的复杂程度。

综合上面的结论,Juggling Pipeline 的部署方案有以下几个特点:

  • 仅使用一块 FPGA 板卡,适用于终端计算。
  • 实现了资源复用情况下最好的吞吐率和延时。
  • 因为使用了 FPGA 可重构技术,使得电路设计更加复杂、受限,同时造成一定的资源浪费。

这里还需要指出的是,目前世界上两大 FPGA 生产厂牌 Xilinx 和 Intel(Altera),都提供了 FPGA 的可重构接口。就我的课题组使用的 Xilinx Series-7 系列的 FPGA 而言,可重构接口的理论速度为 400 MB/s,一个经过压缩的可重构区域的位流文件(BIT 文件)大小假设为 2-4 MB,那么重构时间为 5-10 ms,该时间是无法优化的。所以本方案仅适用于每个流水级的计算时间在 ms/10ms 量级的应用,如果计算时间远低于该量级,那么重构就会造成大延时。

2.2 部署方案的实现

课题组的学长之前在 Xilinx 的 VC709 开发板上实现了 SqueezeNet,可以完整部署在 FPGA 上,但如果在之前设计的 FPGA-CPU 异构计算平台上,则无法实现完整的部署,故考虑使用 Juggling Pipeline 来进行部署和实现。Juggling Pipeline 的实现方法对于各种计算单元基本一致,只有接口要根据需求进行调整。

之前提到了 Xilinx 提供的可重构接口,具体来说在 Series-7 系列中,提供的接口是 ICAPE2,根据王琪的意见,调用这个接口时,实际调用的是一个片上硬核,对 FPGA 进行实时的局部动态重构。该接口工作在 100 MHz,宽度为 32 bit(即 4 Byte),所以传输带宽为之前提到的 400 MB/s。Xilinx 提供了两个 IP 核对该接口进行封装,一个是 Hardware ICAP(简称 hwicap),一个是 Partial Reconfiguration Controller(简称 prc)。hwicap 仅提供软件触发重构,且必须手动从外部(PCIe 或 DDR)传入位流文件,且没有成功或失败反馈,配置也相对简单。prc 提供软件触发和硬件触发重构,可以将位流文件事先存储在 DDR 或 Flash 中,自动进行加载,有成功或失败反馈,配置相对复杂。

FPGA-CPU 异构计算平台包含一个 MicroBlaze 软核,可用于软件编程,理论上可以使用软件触发,即使用 hwicap 进行设计,重构触发在计算过程中需要反复执行,直接影响到计算效率,故仍然考虑使用硬件触发方式,使用 prc 进行设计。


图示为 prc 的逻辑框图,可以看到 prc 中包含若干个 Virtual Socket Manager,分别对应各个 FPGA 上各个重构区域,同时包含一个 Fetch Path,可以通过 AXI MM 总线接口从Configuration Library(DDR、Flash 或其他外部存储设备)加载位流文件,并重构到目标的重构区域。HW Triggers 为硬件触发信号,HW Reset 为标志重构完成的复位信号。prc 还提供一个 AXI4-Lite 的寄存器控制接口,也可以用来进行软件触发。


为了对硬件触发和 Juggling Pipeline 的工作流程进行控制,需要设计一个状态机。该状态机将重构过程和计算过程视为一致,总是发出开始信号,接收到结束信号标志该部分完成,等到所有部分均完成(包括重构和计算),即进入下一个流水线状态。

另外需要特别指出的是,当一个区域处于重构状态时,通往该区域的信号(例如存取数据的 AXI MM 总线信号)处于不定态,如果不进行任何处理,可能会导致整个运算电路的 halt 或崩溃(这种情况在调试过程中曾反复困扰我)。所以需要按照 Xilinx 的建议使用 Partial Reconfiguration Decoupler IP 核,Decoupler 在重构期间替代计算单元,对所有关键信号进行置高或置低处理,以保证静态点路的正常工作,在重构完成后再将信号的控制权交还给重构完成的计算单元。实际上 Decoupler 起到了一个 MUX 的作用。


图示为部署 Juggling Pipeline 的系统框图,其中的灰色区域均为静态系统电路,白色部分为可重构的区域,仍以六层神经网络为例,三个 Virtual Socket 表示 FPGA上的三个可重构区域。


2.3 与传统方案的比较


图示为分布式计算方案,传统重构方案和本方案的各个指标对比。其中红色表示该项为最差。


3 SqueezeNet 案例

根据 2.2 对部署方案实现的方法,对 SqueezeNet 的前四层进行了部署测试,片上存在两个可重构区域,实现一个最小测试系统。测试成功,计算结果与软件仿真结果一致。


图示为 SqueezeNet 前四层部署在 VC709 开发板上的截图。其中整个方形区域为 FPGA 片上所有资源,红色部分为系统静态电路,左上方两个方形为可重构区域,可重构区域中的电路已被挖去,剩余的白色标记为可重构区域电路与系统静态点路的接口。

因为要进行可重构区域不同配置的综合-实现,系统静态电路需保持不变,红色表示该部分电路已被锁死,重新综合-实现时,不会再被重新修改。


图示为 SqueezeNet 前四层部署在两个可重构区域的截图。


以上。祝好运!

Hanchen Ye
Hanchen Ye
PhD Student in UIUC

This dream will last forever.