Spark 3.0 新特性——加速器感知的任务调度

原文

本文翻译自 Spark 官方 JIRA 和设计文档——SPIP: Accelerator-aware task scheduling for Spark


背景和动机

GPU 和其他加速器已经被广泛地用来加速特殊的工作负载,例如深度学习和信号处理。

人工智能社区的用户大量使用 GPU,同时他们经常需要 Apache Spark 来加载和处理大型数据集,以及处理类似流数据的复杂数据场景。

YARN 和 Kubernetes 在最近的版本中已经支持 GPU。

尽管 Spark 支持这两个集群管理器,但 Spark 本身并不感知它们暴露的 GPU,因此 Spark 无法正确请求 GPU 并为用户调度。

这就带来了很关键的缺口,我们无法做到统一大数据和人工智能的工作负载并且使终端用户生活得更加简单。

为了让 Spark 感知 GPU,我们将在上层做出两项重大的更改:

  • 在集群管理器级别,我们更新或升级集群管理器,以包括 GPU 支持。然后,我们为 Spark 暴露了用户接口,以向其请求 GPU。
  • 在 Spark 中,我们更新其调度程序,以了解分配给 Executor 的可用 GPU、用户任务请求,并将 GPU 正确分配给任务。

基于在 YARN 和 Kubernetes 中为支持 GPU 和一些离线原型所做的工作,我们在 Spark 3.0 中实现了必要的功能。


YARN 支持

关于 YARN 请参考我的博客——谈谈你对YARN这个框架的理解?

GPU 调度支持要求 YARN 3.1 或更高版本(可能 3.1.2+)。

这里介绍了用户怎样给他们的 YARN 集群来配置 GPU 调度的详细信息。

YARN 支持 GPU 的自动检测或者管理员如果想要的话可以明确指定暴露给 YARN 的 GPU 设备。

当请求 Executor 的 YARN 容器时,Spark 在 YARN 容器请求中将 Executor 需求的 GPU 数量映射到yarn.io/gpu资源上面。

无论有没有 Docker 容器,YARN 都有着 GPU 隔离性,因此 Executor 将阻止使用未分配给 YARN 容器的 GPU,假定管理员已经恰当地进行了配置。

  • (P1 优先级)对于 亲和性/反亲和性的支持,Spark 可以利用YARN Placement Constraints来帮助 YARN 知道 Spark 会喜欢co-located的容器或者明确非co-located的容器。但是,由于默认情况下将其禁用,因此需要配置 YARN 集群以支持它。

  • (P2 优先级)对于 GPU 类型变化的和作业需要特定 GPU 的异质集群,用户可以利用 YARN 的节点标签将节点类型和设置队列分隔开,这些设置队列只会在这些节点类型上分配容器。从 Hadoop 3.2 开始,YARN 开始支持节点属性,该属性可用于标记节点上的 GPU 类型,并且这些标签可以与请求上的放置约束一起使用,以确保请求正确的节点类型。

  • (P2 优先级)YARN+Docker 支持。如果集群管理员配置了允许的运行环境,则 YARN 支持在Docker 容器中运行应用程序任务。详细信息在这里介绍。 Spark 的主要目的是为了提供类似 ML 库、特定的 Python 版本等的依赖性从而提供一个更简单的设计。在标准安装路径上,例如/usr/bin/usr/lib,而不是将这些依赖强硬地纳入 YARN 的分布式缓存中作为 .tgz 档案并且修改应用程序的PATHLD_LIBRARY_PATH以找到它们。

Docker 容器可以运行应用程序,日志和在预期路径下绑定到容器中的分布式高速缓存目录,因此应用程序可以通过分布式缓存(例如:作业配置,用户 JAR 包等)决定用哪个依赖,运行哪个 Docker 镜像(例如:Python,R,ML Libs等)。

由于日志目录被绑定到容器中,因此该应用程序为 YARN 提供了和非 Docker 任务相同的日志。

默认情况下,Docker 容器使用主机网络运行,因此从网络角度来看,它就像非 Docker 任务一样运行。当前也支持桥梁网络,但在 Hadoop 3.1 中可能不稳定。

由于 YARN 将 GPU 分配给 Executor,因此所选的 GPU 将暴露于 Docker 容器中。 Spark Executor 需要以一种和非 Docker 场景下相同的方式来发现分配的 GPU。 从 GPU 调度的角度来看, YARN Docker 的支持应该是个正交问题,YARN 集群管理员的主要职责就在于配置。 Spark 不需要明确支持潜在地提供引用 Docker 镜像的特性,例如通用的 Spark-on-YARN 用例。

Spark不需要明确支持该功能,只需要为常见的 Spark-on-YARN 场景来提供引用 Docker 镜像的能力。


Kubernetes 支持

关于 Kubernetes 请参考我的博客——Kubernetes 是什么?

Kubernetes 使用device plugin模型来支持节点上的加速器设备。链接提供了 K8S 中当前可用的加速器插件的列表,包括 NVIDIA,AMD,Intel 的插件。每个设备插件在准备节点时都有其唯一的要求集合。这里列出了为Nvidia GPU device plugin准备节点所需的步骤,包括安装必要的 GPU Driver并将 NVIDIA 设置为 Docker 的默认运行时。

作为 Spark+K8S 用户,我可以使用 spark-submit 将应用程序提交给 Kubernetes 集群。 链接running Spark on Kubernetes描述了非 GPU 工作负载是怎么工作的。特别的:

  • spark-submit上,Spark 首先创建一个在 Kubernetes Pod 中运行的 Driver。

关于 Kubernetes Pod 请参考我的博客——Kubernetes 中的 Pod 是什么?

  • Driver 然后创建 Executor,这些 Executor 也在 Kubernetes Pod 内运行并连接到它们,然后执行应用程序代码。
  • 应用程序完成后,Executor Pod 终止并清理。
  • Driver Pod 保存日志,并保持在 Kubernetes API 中的“完整”状态,直到最终垃圾收集或者手动清理。

在 K8S 中指定用于任务的 GPU 数量(RDD Stage,Pandas UDF)类似于 Standalone 和 YARN 模式:要么设置spark.task.gpusspark.executer.gpus的全局默认值,要么在RDD Stage期间每个任务都覆盖默认的配置等等。

  • 在两种场景下:GPU,CPU,内存资源将会映射到任务和 Executor 的 POD 规格清单中。
  • 对于 GPU 资源,K8S 可以将它们作为扩展资源启用,并且可以在vendor-name/gpu标签下指定(scheduling GPUs这个页面查看细节)。

  • (P0 优先级)为了自动发现 GPU 资源支持,上述组件在准备过程中安装在节点上,每个节点上的 GPU 将自动发现并传达给 K8S API 服务器。可以运行kubectl describe node命令,以验证每个节点报告的 GPU 数量是否正确。

  • (P0 优先级)对于 GPU 设备的隔离性,在任务代码中,Spark 应检索分配的 GPU 的索引并将其用于计算。由于 Kubernetes 使用cgroups运行,因此每个 Executor 只会看到分配给它的 GPU 设备。对于 Executor 内部运行的 Spark 任务,我们需要验证相同的行为。

  • (p2 优先级)对于数据本地性和亲和性的支持,Kubernetes 中通过节点选择器来使用标签进行放置选择,这可以提高部分的 CPU 亲和性。进一步的数据本地性和亲和性将需要机架等的拓扑信息,以后将添加。

  • (P2 优先级)K8S+Docker 支持。 Kubernetes 协调容器,并支持包括 Docker 在内的一些容器运行时。 Spark(2.3+版本)带有可用于此目的的 Dockerfile 并根据特定应用需求进行定制。使用Kubernetes,这是运行 Spark 应用程序的主要模式。

    • 配置参数spark.kubernetes.container.{driver/executor/}.image可用来在仓库中指定镜像位置。
    • 对于使用 Docker 运行 GPU 应用程序的,工作节点上需要其他组件:例如,对于 nvidia-docker,用来使用 Docker 在NVIDIA GPU 上运行。

除 GPU 数量外,指定 GPU 类型将是 P1 优先级的要求。由于我们仅支持同质的 GPU 类型为 P0,因此 3.0 版本不需要。以后再支持异质 GPU 类型。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值