dyweb / papers-notebook

:page_facing_up: :cn: :page_with_curl: 论文阅读笔记(分布式系统、虚拟化、机器学习)Papers Notebook (Distributed System, Virtualization, Machine Learning)
https://github.com/dyweb/papers-notebook/issues?utf8=%E2%9C%93&q=is%3Aissue+is%3Aopen+-label%3ATODO-%E6%9C%AA%E8%AF%BB
Apache License 2.0
2.14k stars 250 forks source link

The OoO VLIW JIT Compiler for GPU Inference #185

Open gaocegege opened 4 years ago

gaocegege commented 4 years ago

https://arxiv.org/abs/1901.10008

gaocegege commented 4 years ago

非常非常非常有趣的工作,竞品应该是 TensorRT TVM 之类的东西

gaocegege commented 4 years ago

这篇文章提出了一个 Out of Order 的 JIT VLIW(超长指令字) GPU Kernel 编译器,来在 GPU 按照时间和空间来共享中找平衡。

目前 Serving 场景基本可以分为两类,分别是对延迟不是特别敏感的 Batch 场景和对延迟敏感的 Interactive 场景。对于前者来说优化的目标是 cost-per-query,而对于后者来说 p99 latency 是优化的目标。

正常来说,如果不 Batch,GPU 的利用率会很低,那如何提高利用率?依靠多路复用是计算机系统里常用的一种方式。比如 CPU 会采取分时复用的方式提高利用率,内存会采取空间复用(space-multiplexed)a.k.a Virtual Memory 的方式进行资源的复用。同样,GPU 同样有类似的两种复用方式。

对于 GPU 的分时复用,每个用到了 GPU 的进程会 own 一个 CUDA context,GPU 会利用一个 on device 的调度器,多路复用不同的 Context。这种方式跟 CPU 的分时复用差不多,都是 interleave,而不是并行。而且跟 CPU 相比,GPU 的 context switch 的 overhead 更高,它需要 flush the execution pipeline

按照空间复用,就是 Nvidia 的 Hyper-Q,和 AMD 基于 SRIOV 的实现。与此同时,CUDA Streams 和 MPS 提供了用户层的按照空间多路复用。

文章中提到,按照空间的多路复用会导致很差的隔离性,以及不可预测的执行时间。

Screenshot from 2019-11-04 11-02-00

文章中的实验结果表明,在奇数个的实例中,实例的 latency 的方差更大,但鉴于实验的数据很少,不排除是随机性造成的。

gaocegege commented 4 years ago

接下来,介绍的就是作者 proposed 的解决方案。作者认为 CUDA API 是 early binding 以及 context-free 的,用户需要指定维数和形状。而作者相信 late binding 和 context-aware 会有更好的表现,更好的表现包括更好的空间复用,更高的利用率,重排序来满足不同 execution 的 latency SLO。

这一章节一共就一页,介绍的不是特别清晰,很多地方搞不懂。

在最后一节,作者说有这么一个 JIT compiler 能够动态地 tradeoff latency 和 throughput。

ganler commented 4 years ago

突然发现了策神的GitHub,然后发现你也看过这篇paper。个人感觉其实OoO想解决的问题就是如何更好的做GPU Sharing in deep learning scenario。关于细节我更加推荐这篇paper: Salus: Fine-Grained GPU Sharing Primitives for Deep Learning Applications。 前几个月自己突然产生了兴趣,有了一个从别的角度提升GPU utilization的想法。当然也只是想想而已... 最后抽时间做成了slides,还希望策神能指导指导。

gaocegege commented 4 years ago

@ganler 这篇文章是 RISELab 的朋友推荐的,GPU Sharing in deep learning scenario 也是我最近关注的一个工业界方向 :-)

Salus: Fine-Grained GPU Sharing Primitives for Deep Learning Applications 还真的没有看过,谢谢推荐,年后找时间读一下

你的 slides 非常有意思,从我个人的经验来看,其中提到的手段是从 user level 来进行更好的共享,但是在工业界就会有一个问题,隔离是一个比较强的需求,像显存隔离,算力隔离等,不知道你对这方面有什么看法

ganler commented 4 years ago

@gaocegege Thank you for your reply! Honestly,我可能还得等我年后开始实习了才能开始积累相关的经验(我目前只是一个喜欢自己瞎钻研的大三本科生)。

然后我的观点是,对于那种有较长的占用云端资源的需求的业务这样做显然是对隔离不好的(比如说我付了钱给aws,要求他们部署我的模型并提供一个持久性的inference服务)。但如果考虑到这种情况,就是一个公司有着多个不同类别的在线模型inference的服务,比如说我有很多APP都有一些模型需要通过公司的集群做一个远程计算,这个时候通过设置较小的window size(做计算调度的任务数范围),就能保证「响应时间」。然后同时我们也想优化「周转时间」和「利用率」,那么我们把公司的有着在线服务需求的众多模型融合一下,通过调度,让其中的某些layer有着更大的batch size,那么在「周转时间」和「利用率」上都会有提示。 其实关于GPU利用率这个东西,据我所知,底层的做cuda 算子的(按peter(https://www.youtube.com/watch?v=Lo1rXJdAJ7w)划分的层次来说,就是Kernel层),他们也是通过一些手段,尽量在单个算子上,提高资源占用率来换取更短的时间

Summarize一下就是,我个人认为我的这个想法能在多个异构(不同模型的inference)请求情况下,联合考虑了「响应时间」,「周转时间」和「利用率」。

  1. 「精度」:把模型拆开并融合,可能会损失精度(但从Song Han的deep compression的结果来看,很多甚至都提高了精度)
  2. 「实现难度」:把模型拆开后,一些深度学习编译器能做的layer fusion会受限制,当我觉得这个的话理论上不是问题,但考虑现有的技术的话,会做不了layer fusion,得等有新的人贡献这种multi-model的fusion。再者是做deep compress的话(Song Han的paper有3个阶段),做到前两个阶段还算好做,要是做Huffman压缩并高效执行的话,还是得自己设计硬件,这样成本就很大了,风险也大。
  3. 我现在提出的主要还是一个big idea吧,细节的算法(layer-level的调度,这种情况下的显存淘汰策略)还是得认真仔细的设计。

感谢策神的指导!!!

gaocegege commented 4 years ago

看你的毕业设计的 idea(不知道是不是毕业设计),是想综合考虑不同的 SLO(latency,throughput,GPU utilization 等),去做更好的共享优化,从学术角度来说是值得一试的,对某些场景下的工业界应用也是有帮助的。

gaocegege commented 4 years ago

不过我个人还是更关注 GPU 虚拟化,或者 Nvidia MPS,腾讯的 vCUDA 这样的通用技术 :-) 这对我们的业务帮助是最大的。这个跟公司业务性质有关系,你的思路对一些场景确实是有帮助的,加油加油

gaocegege commented 4 years ago

@ganler 刚刚给你发了一封邮件附上了我的微信 ID,可以多多交流

ganler commented 4 years ago

@gaocegege 嗷!太感谢了!我也一直希望能多和各位交流而不是单打独斗!btw,这个不是毕设,只是一个大三学生在业余无聊的情况下,对自己想法的一个记录(捂脸🤦‍♂️

at15 commented 4 years ago

@ganler tql ... 我大三的时候只是跟 @gaocegege 吃外卖玩游戏 ... (还是大四的时候 ...

gaocegege commented 4 years ago

@at15 死在沙滩上