联手体系结构专业委员会:“用户态GPU池化技术”术语发布
本期发布术语热词:用户态GPU池化技术(User-space GPU Pooling)。
用户态GPU池化技术
作者:陈飞(趋动科技)张伟韬(趋动科技)李诚(中国科学技术大学)
开篇导语
用户态GPU池化技术是指在用户态下对GPU做池化管理的技术。随着人工智能领域的飞速发展,涌现出一大批新的AI应用以及使用场景,为了支撑这些新场景下AI任务的开发与运维,需要构建面向AI场景的GPU池化技术。GPU池化技术以GPU虚拟化为基础,突破了传统GPU虚拟化技术只能支持GPU共享的限制,融合了GPU共享、聚合和远程使用等多种硬核能力,打造全能型软件定义GPU,解决当前用户痛点。
InfoBox:
中文名:用户态GPU池化技术
外文名:User-space GPU Pooling
简介:UGP
学科:GPU虚拟化、计算机体系结构
实质:面向AI应用场景下的GPU管理技术,打造全能型软件定义GPU,让用户更加方便高效的使用GPU。
一、概述
当前,由人工智能引领的新一轮科技革命和产业变革方兴未艾。人工智能技术作为推进中国数字经济发展的核心底层技术之一,将在未来很长一段时期,在数字经济和实体经济深度融合的过程中,扮演关键角色。
进入2023年以来,大模型在人工智能领域受到越来越多的关注。众所周知,大模型具备通用性、泛化性、能有效降低AI开发门槛的特性。因此越来越多中国企业开始接触大模型,并积极探索业务与大模型的结合点,努力开发更先进的智能化产品,提升产品的智能化水平,提升核心竞争力。
然而,AI运行需要大量的算力资源, 特别是GPU,需要通过GPU提高模型的训练和推理部署速度。大模型的到来加剧了这个过程。根据OpenAI数据,训练GPT-3 175B的模型,需要的算力高达3640 PF-days(即以1PetaFLOP/s的效率要跑3640天)。
对大多数企业而言,充分利用现有GPU,让其在新兴大模型与传统业务模型之间充分轮转与复用,最大化发挥GPU应有的效能,是当下企业的头等大事。与CPU不同,GPU有其独特的生态特点与复杂性,因此要将GPU虚拟化实现共享经济,限制条件会更多,难度会更大。而且,如果只是做狭义上的GPU虚拟化,解决的仅仅只是GPU共享问题,比如大模型需要的GPU按需灵活调度,多业务的分时复用,任务排队与优先级,业务的热迁移等,狭义的GPU虚拟化都无法实现。
目前有若干种软件技术方案能实现GPU虚拟化,这些方案可以分为内核态虚拟化和用户态虚拟化两类。本文主要论述这两种方案的差异,以及要实现完整的GPU池化到底需要怎样的方案。
二、内核态与用户态解析
以英伟达的GPU为例,应用到硬件从上至下分为用户态、内核态、GPU硬件三个层次(见图1)。
用户态层:用户态是应用程序运行的环境。各种使用英伟达GPU的应用程序,比如人工智能计算类的应用,2D/3D图形渲染类的应用,都运行在用户态。为了便利编程以及安全因素,英伟达提供了用户态的运行库CUDA(Compute Unified Device Architecture)作为GPU并行计算的编程接口(类似的接口也包括由社区共同制订的OpenGL、Vulkan接口等),应用程序可以使用CUDA API来编写并行计算任务,并通过调用CUDA API与GPU用户态驱动进行通信。GPU用户态驱动再通过ioctl、mmap、read、write接口直接和GPU的内核态驱动进行交互。
内核态层:该层主要运行的是GPU的内核态驱动程序,它与操作系统内核紧密集成,受到操作系统以及CPU硬件的特殊保护。内核态驱动可以执行特权指令,提供对硬件的访问和操作接口,并对GPU硬件进行底层控制。出于系统安全考虑,用户态的代码只能通过操作系统预先定义好的标准接口(Linux下有例如ioctl,mmap,read,write 等少量接口),调用内核态的代码。通过这些接口被调用的内核态代码一般是预先安装好的设备的内核态驱动。这样保证内核态和用户态的安全隔离,防止不安全的用户态代码破坏整个计算机系统。GPU的内核态驱动通过PCIe接口(也可能是其他硬件接口)以TLP报文的形式跟硬件进行通信。
特别的,包括英伟达在内的各类AI芯片产品的内核态和用户态之间的接口定义并不包含在例如CUDA、OpenGL、Vulkan等协议标准里面,他们也未曾向行业公开这一层的接口定义。因此各类行业应用也不会基于这一层的接口进行编程。
图1:CUDA软件栈
三、两种虚拟化技术难度解析
从技术可能性的角度来看,用户态与内核态各有相应的接口可以实现GPU虚拟化或者GPU池化:用户态的CUDA、OpenGL、Vulkan等应用运行时接口;内核态暴露的 ioctl、read、write等设备驱动接口。
用户态虚拟化:利用CUDA、OpenGL、Vulkan等标准接口,对API进行拦截和转发,对被拦截的函数进行解析,然后调用硬件厂商提供的用户态库中的相应函数(见图2)。拦截CUDA等用户态接口不需要在OS内核层进行设备文件的插入,因为这些接口的使用方式是操作系统在运行可执行文件的时候(例如Linux下的elf二进制),由操作系统的加载器自动在系统中按照固定的规则来寻找其依赖的外部接口,学术名称叫做符号(symbol)。那么根据操作系统寻找依赖的规则,很容易可以通过替换symbol的来源,使得当可执行文件发生例如CUDA接口调用的时候,调用的不是英伟达的闭源用户态软件提供的接口,而是一个经过修改后的同名接口,从而拦截到例如CUDA接口的调用。
经过API拦截之后,用户态虚拟化方案还可以利用RPC的方式进行远程API Remoting(见图2),即CPU主机可以通过网络调用GPU主机的GPU,实现GPU的远程调用。如此一来,多个GPU服务器可以组成资源池,供多个AI业务任意调用,达到实现GPU池化的目的。用户态虚拟化是一种软件的实现方案。目前业内已经成型的产品有:趋动科技的OrionX GPU池化产品,VMware的Bitfusion产品。这类技术方案拥有几个优点:
1、CUDA、OpenGL、Vulkan等接口都是公开的标准化接口,具有开放性和接口稳定性。所以基于这些接口的实现方案具有很好的兼容性和可持续性。
2、因为该方案运行在用户态,因此可以规避内核态代码过于复杂容易引入安全问题的工程实践,可以在用户态通过复杂的网络协议栈和操作系统支持来实现及优化远程GPU的能力,从而高效率地支持GPU池化。
3、由于该方案工作在用户态,从部署形态上对用户环境的侵入性最小,也最安全,即使发生故障也可以迅速被操作系统隔离,而通过一些软件工程的设计可以有很强的自恢复能力。
当然,这类方案也有缺点:相比于内核态接口,用户态API接口支持更复杂的参数和功能,因此用户态API接口的数量比内核态接口的数量要高几个数量级。这导致在用户态层实现GPU虚拟化和GPU池化的研发工作量要比在内核态实现要大得多。
图2:用户态API转发
内核态虚拟化(见图3):跟上述用户态拦截API类似的,第三方厂商所做的内核态虚拟化方案通过拦截ioctl、mmap、read、write等这类内核态与用户态之间的接口来实现GPU虚拟化。这类方案的关键点在于需要在操作系统内核里面增加一个内核拦截模块,并且在操作系统上创建一些设备文件来模拟正常的GPU设备文件。例如,英伟达GPU在Linux上的设备文件有/dev/nvidiactl、 /dev/nvidia0等多个文件。因此,在使用虚拟化的GPU时,把虚拟化出来的设备文件mount到业务容器内部,同时通过挂载重命名的机制伪装成英伟达的同名设备文件名,让应用程序访问。这样在容器内部的应用程序通过CUDA去访问设备文件的时候,仍然会去打开例如/dev/nvidiactl 和 /dev/nvidia0这样的设备文件,该访问就会被转发到模拟的设备文件,并向内核态发送例如ioctl这样的接口调用,进而被内核拦截模块截获并进行解析。目前国内的qGPU和cGPU方案都是工作在这一层。这类技术方案的优点是:
1、有较好的灵活性,而且不依赖GPU硬件,可以在数据中心级和消费级的GPU上使用。
2、在GPU共享的同时,具备不错的隔离能力。
3、由于只支持运行在容器环境中,研发工作量相比用户态方案要小得多。
这类方案由于工作在内核态,缺点也是显而易见的:
1、需要在内核态层插入文件,对系统的侵入性大,容易引入安全隐患。
2、由于英伟达GPU内核态驱动的ioctl等接口以及用户态模块都是闭源的,接口也不开放,因此只有英伟达自己可以在这层支持所有的GPU虚拟化能力,其他第三方厂商只能通过一定程度的逆向工程来实现对这些接口的解析。这种行为存在着极大的法律风险和不确定性,可持续性远低于用户态方案。
3、第三方厂商由于缺少完整的接口细节,目前只能通过接口“规避”的方式来支持。所谓“规避”,简单来说就是只解析必要的少数几个接口,其他的不劫持直接放过。为了方便实现“规避”效果,这类方案目前都只能支持基于容器虚拟化的环境(因为很容易实现),无法支持非容器化环境以及KVM虚拟化环境,更加无法跨越操作系统支持GPU池化最核心的远程GPU调用,因此这类方案不是完整的GPU池化方案。
图3:内核态API转发
上述两种虚拟化方案在经过接口拦截之后,就可以在当前的接口调用中被激活,接下来就是对该接口进行解析。不管是 ioctl 接口还是 CUDA接口,从计算机设计上,都可以表达为interface_name(paramerA, parameterB, …)这样的形式。也就是接口名称,接口参数(返回值也是一种参数形式)。而不管基于哪一层接口的拦截,这里的解析又分为两种:
1.同一个进程空间的接口解析(见图4):在现代操作系统中,不管在用户态还是内核态,代码都执行在由CPU硬件 + 操作系统维护的一个进程空间里面,在一个进程空间里面有统一的进程上下文(context),并且所有的资源在进程空间内都是共享的,视图是统一的,包括访存地址空间(address space),也包括GPU设备上的资源。这个现代操作系统的设计可以为同一个进程空间的接口解析带来极大的便利。因为对于一个接口interface_name(paramerA, parameterB, …),即使存在不公开含义的参数,例如parameterB是不公开的,但是利用一个进程空间内所有的资源都是共享且视图统一的这个特点,只要确定该部分内容不需要被GPU虚拟化模拟执行所需要,那么虚拟化软件可以不需要对其进行解析,在截获之后,直接透传给英伟达自己的闭源模块就可以。实际上,只有少量接口,少量参数会被需要在一个进程内被解析并且模拟执行,因此选择这个技术路线可以“规避”掉绝大多数接口、参数的解析工作。具体以针对英伟达的GPU为例,只有非常少的接口、参数需要被真正解析并模拟执行。一些产品之所以能在非公开的内核接口层实现GPU虚拟化,是利用了同一个操作系统的特点,基于少量接口信息,来达到GPU虚拟化的目的。但是这样的技术路线也有一个非常明显的限制,就是只能在同一个进程空间内进行接口的拦截、解析和执行。因此这种技术路线从原理上就无法支持跨OS内核的KVM虚拟化,更无法跨越物理节点做到远程调用GPU。
2.不同进程空间的接口解析(见图4):当GPU应用所在的操作系统和管理物理GPU所在的操作系统是两个不同的操作系统的时候,要达到GPU虚拟化、GPU池化的目的,就需要跨进程对选定的GPU接口层进行跨进程的接口解析。典型的场景如 KVM虚拟机,还有跨物理节点调用GPU。由于应用程序和GPU管理软件栈(例如GPU驱动)已经不在一个操作系统的管理下,因此资源就不再是共享的了,视图也不再是统一的了。例如,同样的一个虚拟地址(virtual address)在不同的进程空间代表的很可能是不一样的内容。所以对于所有接口interface_name(paramerA, parameterB, …),都要进行完善的解析、处理,并通过例如网络的方式跨越操作系统进行传送。以英伟达的 CUDA 为例有数万个接口,需要对每一个接口都进行跨进程空间的接口解析,然后进行行为模拟。因此,在不公开的接口层进行跨进程空间的接口解析,原理上是行不通的。
图4:相同/不同进程空间的接口拦截方式
经过接口解析之后,则需要向GPU应用提供一个模拟的GPU执行环境,这个模拟的动作是由GPU虚拟化和GPU池化的软件来完成的。不同软件提供的模拟的能力是有差异的,但是其基础的能力,都是要保持对上层应用的透明性,使得应用不需要改动实现,不需要重新编译。
对于GPU虚拟化和资源池化,由于在接口层的的选择上有两个分支,在接口解析上也有两个分支,所以排列组合起来有4种可能,下面对4种方式做一个对比。
通过对比这4种可能的方式,我们做个总结:
①内核态方案仅能在同一个进程空间工作,无法跨机,因此无法实现GPU池化。
②内核态方案要在同一个进程空间实现GPU虚拟化是相对简单的。
③只有用户态方案可以实现跨不同进程空间工作,可以跨机,因此可以实现GPU池化。
④用户态方案要想跨不同进程空间实现GPU池化,有大量接口需要解析,难度与门槛很高。
四、GPU池化功能定义
借鉴软件定义存储解决存储问题、软件定义网络解决网络问题,GPU算力调度与共享的问题也需要用完整的软件定义方案来解决。GPU池化就是为这个完整的软件定义GPU方案而设计的。
采用软件定义算力理念的GPU池化技术,站在整个数据中心的高度,以GPU虚拟化为基础,突破了传统GPU虚拟化技术只能支持GPU共享的限制,融合了GPU共享、聚合和远程使用等多种硬核能力,打造全能型软件定义GPU。通过把物理GPU抽象成类似于分布式存储,可以通过网络在数据中心内全局统一运维和管理、任意使用的抽象资源,GPU池化技术解决了当前用户的痛点。
具体来说,GPU池化须具备以下几个能力:
①细粒度切分GPU卡的能力:按算力与显存两个维度,实现1%算力颗粒度,1MB显存颗粒度,以提供与需求相匹配的小于一块物理GPU卡的算力。
②远程调用GPU的能力:即在一台服务器上部署AI任务,可以通过网络远程调用另一台服务器上的GPU资源进行加速,本机无需GPU卡。
③跨服务器聚合资源的能力:把集群里的多块GPU卡聚合给单个运算任务,让单个任务可以方便使用更多的GPU卡资源而无需关注单机的GPU数量。
④随需应变的能力:按算力需求进行GPU资源的动态伸缩,无需重启虚机或容器。
⑤支持GPU资源的超分和超售,这也是云厂商希望具备的能力。
⑥GPU显存的扩展,可以将CPU的内存用于扩充GPU的物理显存,例如,可以支持CUDA程序在1个只有32G显存的GPU上,分配和使用超过32G显存。
⑦在GPU资源不足的情况下,可以对GPU任务进行排队以及队列优先级的设置。
⑧在多个GPU任务出现资源争抢时,可以对高优先级任务进行资源保障。
⑨支持同一个进程里面CUDA计算和渲染混合使用。
⑩支持物理GPU和虚拟GPU的统一管理,物理和虚拟GPU可按需互相转换。
⑪同时支持KVM虚拟机、Docker容器和K8S三种架构下的GPU虚拟化和池化,且三种架构下能力一致。
五、GPU池化具备更广阔的应用场景
传统上的GPU虚拟化技术,或者叫GPU切片技术,基本上还是基于硬件的思维,只能对本地物理机上的GPU进行切分,把一个物理GPU卡变成若干个虚拟GPU小卡,再将小卡以静态分配的形式给到虚拟机或容器。这类方案实现的GPU虚拟化功能单一,实现起来难度系数并不大。
远程调用是重要的技术分水岭(见图5),是从传统GPU虚拟化走向GPU池化的技术基础。有了远程调用技术的加持后,原本固化的GPU可以根据业务的需求进行动态分配和管理。该技术可以在多主机之间灵活地调配GPU资源,提高系统的灵活性和可扩展性。典型应用场景有:
1、CPU与GPU解耦:通过远程调用GPU,可以无需在每台主机上都安装独立的GPU。这样可以节约硬件成本,并减少能源消耗。
2、扩大调度域:远程调用GPU可以使多台计算机或服务器共享计算资源,GPU的算力辐射范围从单机扩大到整个数据中心。这样可以简化调度流程,扩大调度域,大幅提高数据中心内GPU的整体效率。
3、高IO预处理:有些IO吞吐高的场景,例如模拟仿真,在预处理环节CPU容易成为瓶颈。单机内部2颗CPU+4到8张GPU的配比明显不符合需求。借助远程调用GPU,这类业务可以部署在多台CPU主机,按需挂载远程GPU,实现CPU和GPU资源弹性组合。
图5:远程GPU调用
4、渲染卡与计算卡灵活搭配(见图6):类似数字人/机器人业务场景,强渲染与大算力需求并存。不同系列的GPU卡有各自的突出特性,比如光线追踪技术常见于工作站系列,大规模张量计算常见于服务器系列,通常不同型号的卡无法在同一主机内混插。通过远程调用,两类服务器各司其职,相互搭配,共同支撑一个应用,实现对强渲染与大算力的同时支持,以及对GPU资源的最大化利用。
图6:渲染卡与计算卡灵活搭配
5、显存超分(见图7):某些AI在线业务存在显著的时间分布特征,比如白天繁忙夜晚空闲。由于业务需实时在线,因此夜晚依然常驻GPU,但是算力利用极低。通过“显存超分”,池化软件会调用系统内存补充GPU显存,在逻辑上扩大GPU显存的承载容量,从而支持多个常驻显存的长尾任务叠加在同一个物理GPU上,提高单个GPU的承载量,充分利用GPU闲置算力。根据业务特点,池化软件还支持不同任务设置不同优先级,从而保证突发高优先级任务的服务质量。
图7:GPU显存超分
6、多元异构算力芯片支持、多种云基础架构支持(见图8):作为一个完整的软件定义GPU产品,首先,GPU池化必须要能够适配国际国内多种异构算力芯片,且池化能力一致,多种芯片融合统一管理,按需智能化调度;其次,GPU池化必须能同时适配多种云计算场景,比如公有云、私有云、KVM虚拟机、容器、K8S、裸金属等,且池化能力一致,支持多种基础架构混合部署,统一管理,综合调度。
图8:异构算力资源池
六、总结
人工智能已经进入大模型时代,以ChatGPT为代表的通用大模型极大拉动了市场对GPU算力的需求。除了通用大模型,服务于B端客户的垂直行业大模型、基于通用大模型的微调等行业应用也需要大量的GPU算力做支撑。然而,受到中美关系、芯片产能等因素的影响,从中期来看,占市场主导地位的NVIDIA GPU的获取成本将会越来越高;从长期来看,国产AI芯片在性能与生态上逐步成熟,将有望突围,实现国产替代。
在此背景下,软件定义GPU是大势所趋。通过软件定义的方式将GPU进行抽象,有利于高成本的GPU物尽其用,也有利于多元异构芯片的统一管理与平滑迁移。
基于用户态的GPU池化技术,扩展了更多的GPU功能,具备了更丰富的应用场景,蕴含了更深的可挖掘潜力,将会成为软件定义GPU的最佳实践。
参考文献:
1、CSDN:《惊人的算力成本背后,自动驾驶公司如何加速研发创新》
2、趋动科技:《论软件定义GPU对AI数据中心优化的必要性》
3、中国计算机学会:《联手体系结构专业委员会:“GPU池化”术语发布 | CCF术语快线》
4、CSDN:《GPU并行计算技术赋能证券业务新发展》
作者介绍
陈飞
研究领域:高性能计算、计算机体系结构、GPU和FPGA虚拟化
邮箱:chenfei@virtaitech.com
张伟韬
研究领域:计算机体系结构、GPU虚拟化
邮箱:zhangweitao@virtaitech.com
李诚
研究领域:人工智能基础计算系统
邮箱:chengli7@ustc.edu.cn
计算机术语审定委员会及术语平台介绍:
计算机术语审定委员会(Committee on Terminology)主要职能为收集、翻译、释义、审定和推荐计算机新词,并在CCF平台上宣传推广。这对厘清学科体系,开展科学研究,并将科学和知识在全社会广泛传播,都具有十分重要的意义。术语众包平台CCFpedia的建设和持续优化,可以有效推进中国计算机术语的收集、审定、规范和传播工作,同时又能起到各领域规范化标准定制的推广作用。新版的CCFpedia计算机术语平台(http://term.ccf.org.cn)将术语的编辑运营与浏览使用进行了整合,摒弃老版中跨平台操作的繁琐步骤,在界面可观性上进行了升级,让用户能够简单方便地查阅术语信息。同时,新版平台中引入知识图谱的方式对所有术语数据进行组织,通过图谱多层关联的形式升级了术语浏览的应用形态。
计算机术语审定工作委员会:
主任:
李国良(清华大学)
副主任:
王昊奋(同济大学)
林俊宇(中国科学院信息工程研究所)
主任助理:
李一斌(上海海乂知信息科技有限公司)
执行委员:
丁 军(上海海乂知信息科技有限公司)
兰艳艳(清华大学)
张伟男(哈尔滨工业大学)
彭 鑫(复旦大学)
李博涵(南京航空航天大学)
委员:
柴成亮(北京理工大学)
李晨亮(武汉大学)
张 鹏(天津大学)
王昌栋(中山大学)
张宁豫(浙江大学)
孔祥杰(浙江工业大学)
魏 巍(华中科技大学)
术语投稿热线:ccfpedia@ccf.org.cn