写点什么

Janus: 基于 eBPF 的 5G 实时 AI 控制器

作者:俞凡
  • 2023-03-05
    上海
  • 本文字数:31229 字

    阅读完需:约 102 分钟

O-RAN 定义的 RIC 模型并不能很好支持对实时性有很高要求的用例,本文定义了一套基于 eBPF 的内联执行架构,从而可以将 RIC 的支持扩展到实时场景。原文: Taking 5G RAN Analytics and Control to a New Level

摘要

Open RAN 为 5G 无线接入网(RAN)引入了模块化和解耦的设计范式,并承诺通过 O-RAN 定义的 RAN 智能控制器(RIC, RAN Intelligent Controller)实现完全的可编程性。然而,由于延迟和安全方面的挑战,RIC 提供的遥测和控制主要局限于较高层面以及较长的时间尺度(>10𝑚𝑠),同时还依赖于难以改变的预定义服务模型。为了解决这些问题,我们提出了一个完全可编程的监测控制系统--Janus,考虑到 RAN 的特殊性,该系统专注于灵活性、高效率和安全性。Janus 建立在 eBPF 基础上,允许第三方以可证明的安全方式在 RAN 的功能组件中直接加载小程序(codelet)。我们用一种新的字节码修补算法来扩展 eBPF,该算法可强制保证小程序运行时的阈值,并以安全的方式收集用户定义的遥测数据。我们建立了 3 个不同类别的应用(共 17 个应用,大多数在现有的 RIC 上无法实现),并在不影响 RAN 性能的情况下部署在 100MHz 的 4x4 MIMO 5G 小区上,从而可以证明 Janus 的灵活和高效。

1. 简介

5G 无线接入网(RAN)的一个关键转变是迁移到 Open RAN 架构,即 RAN 功能的虚拟化(vRAN)和解耦。这种方法允许供应商以更快的速度为不同组件提出独特的解决方案,从而促进创新。此外,无线智能控制器(RIC)[27, 31]允许第三方通过 O-RAN[19]标准化开放接口建立数据驱动的、与供应商无关的监测和控制应用[9, 20],从而更好的优化网络。


尽管愿景引人注目,但相关创新很大程度上仍处于非常早期的阶段,主要有两个原因。首先,RAN 以很高频率产生大量数据,为 RIC 应用捕获、传输和处理数据会给计算和网络带来巨大压力。为了克服这个问题,由 3GPP[13,14]标准化的传统方案是定义一小套关键性能指标(KPI)集合,每几秒钟或几分钟收集一次。O-RAN RIC 通过提供一套新的标准化聚合 KPI 和数据源[25],扩展了这一方案。每个 KPI 都通过服务模型(一种静态 API 形式,作为嵌入 vRAN 功能的 RIC 代理的一部分[24])定义,并规定了哪些数据可以被收集、以何种颗粒度收集。然而,这种方法发展缓慢,而且不能灵活扩展,任何不适合现有服务模型的用例,都需要指定定义了不同 KPI 集的新服务模型,并与选定的 RIC 和 RAN 供应商合作,增加对这种服务模型的支持,然后经历漫长的标准化过程,说服所有 O-RAN 供应商支持并实施这种模型。


其次,许多关键的 RAN 操作,如用户无线资源调度和功率控制必须在期限内完成,通常是几十𝜇s 到几 ms 不等。为了满足最后期限,任何相关控制逻辑和推理必须在 vRAN 功能内部运行,而不是在 RIC 上,RIC 的设计是为了处理时间尺度>10ms[78]的应用。现有 RIC 方法通过指定针对特定用例的服务模型来处理这个问题,每个模型都有一套支持策略(例如,从𝑁个可用无线资源调度算法中选择一种)。然而,与数据收集的情况类似,由于无法灵活引入新的控制和推理算法,因此很难扩展。此外,许多 vRAN 操作具有实时性要去,意味着为了支持新服务模型而增加的任何新功能必须在 vRAN 处理期限内完成,超出期限可能会导致性能下降[45],甚至使 vRAN 崩溃(正如第 7.2 节中所示),这使得 RAN 供应商不愿意增加新的功能和服务模型。


为了解决这些问题,我们提出了 Janus,一个提供动态监测和控制 vRAN 功能的系统。Janus 扩展了 RIC,允许运营商和受信任的第三方编写自己的遥测、控制和推理代码(我们称之为小程序 codelet),这些代码可以在运行时部署在不同的 vRAN 组件上,不需要供应商的任何帮助,也不会干扰 vRAN 的运行。小程序通常在 vRAN 关键路径上内联执行,直接访问所有重要的原始内部数据结构,收集任意统计数据,并做出实时推理和控制决策。


虽然 Janus 通过将 vRAN 实现和数据收集、控制操作解耦,大大增强了 RIC 的能力,但也带来了一系列挑战。第一个挑战与灵活性有关,目前还不清楚构建有用的应用需要哪些以及多少 RAN 监控数据,以及哪些控制功能应该暴露给小程序开发者。我们通过识别标准 vRAN 架构中的关键位置和接口(称之为钩子 hook)来解决这个问题,接口可以从若干收集点(collection point)收集丰富多样的数据,从而实现广泛的实时控制应用。我们还建立了一个工具链,允许开发者定义任意的数据输出结构,将收集的数据发送给 RIC。最后,我们确定了一小部分精心选择的控制功能(我们称之为执行器功能 actuator functions),可以由加载在控制钩子中的小程序调用,实时改变 RAN 的行为(如改变功率、资源块分配等)。通过第 4 节中展示的用例,可以证明 O-RAN 服务模型可以作为 Janus 小程序,实现快速有效的控制和推理操作(例如,无线资源分配和干扰检测),而这在 O-RAN RIC 中是不可能的。


第二个挑战是执行的安全性。虽然小程序是由受信任的各方提供的,但仍然可能出现无效内存访问或过长执行时间,从而导致错误和低效,造成数据损坏,超过实时完成时间,最终导致 vRAN 功能崩溃。我们通过提供基于 eBPF[3, 92]的沙盒执行环境来解决这一挑战,eBPF 解决了 Linux 内核[2]中的类似问题。小程序由 C 语言编写,被编译成 eBPF 字节码,字节码在 vRAN 控制和数据路径中通过内联的 eBPF 虚拟环境运行,可以直接访问选定的内部 RAN 数据结构和控制功能。在加载小程序之前,eBPF 执行环境会对字节码[48, 92]进行静态检查,只允许运行内存访问安全的小程序。


我们进一步扩展该模型,使其符合 vRAN 要求,通过一种新颖的 eBPF 字节码修补机制,我们为小程序的执行时延加入了硬性的𝜇s 级控制,该机制允许强制中断运行超过一定时间阈值的小程序。此外,我们还扩展了小程序的静态验证过程,以覆盖新引入的灵活的输出数据结构。我们还做了一些优化,确保在 fastpath(Janus 小程序运行的地方)支持当前还不知道的设计,使 Janus 对 vRAN 的性能影响最小。最后,我们将 Janus 与 CapGemini 公司[35]的商业 5G vRAN 协议栈(基于英特尔 FlexRAN 参考设计[57])和 OpenAirInterface(OAI)[26]的开源 4G/5G 协议栈集成。


综上所述,我们作了如下工作:


  • 提出了第一个安全、可编程框架,以最小的计算开销为 vRAN 动态引入灵活的监测和控制能力(第 3 节),并通过在其上开发新的遥测、控制和推理应用来说明其功能(共 17 个应用)(第 4 节)。

  • 提出并构建强制限制小程序运行时间和数据安全收集的机制,以确保 vRAN 满足安全和延迟要求(第 5 节)。

  • 实现并优化了 Janus(第 6 节),并进行了全面评估(第 7 节)。


我们希望将来 Janus 能与 O-RAN RIC 集成,以进一步加强 Open RAN 架构,实现可观察、可编程和自动化的最终目标。

2. 背景及动机

2.1. vRAN 架构

如图 1 所示,5G RAN 由若干层组成(如 PHY、MAC、RLC),每一层负责一组不同的控制和/或数据平面操作。例如,PHY 负责信号处理,MAC 负责用户设备(UE, UserEquipment)之间的无线资源实时调度。这些层分布在三个网络功能中,称为无线电单元(RU, Radio Unit)、分布式单元(DU, DistributedUnit)和集中式单元(CU, Centralized Unit),CU 又被进一步分解为控制面和用户面组件(CU-CP 和 CU-UP)。RU 通常基于 ASIC 或 FPGA,而 CU 和 DU 是虚拟化的(即 vCU 和 vDU),运行在带有通用处理器和加速器的商品硬件上[56, 90]。不同组件和层有不同的时延要求(参见[32]),并以不同速率产生事件和数据,如图 1 所示。


图 1: vRAN 体系架构和流程概要以及吞吐量要求。


vRAN 组件之间的通信是通过 O-RAN[19]和 Small Cell Forum[41]等标准化组织定义的开放接口实现的,而可编程性是通过近实时 RIC[47]来实现。网络运营商在 RIC 上安装应用程序(O-RAN 术语中的 xApps),以收集数据并进行推理、闭环网络优化或以近实时(>10ms)的反应速度报告问题。vRAN 组件的数据收集和控制是通过供应商嵌入 vRAN 功能的服务模型来实现的,这些模型定义了每个 xApp 的数据报告类型和频率以及 RIC 可以执行的控制策略列表。

2.2. vRAN 可编程性的限制

RIC 用例最初的重点是网络自我优化、异常检测和粗粒度无线资源分配[60, 75, 78, 85]。在这样的用例中,重要的网络事件和控制决策以较低频率发生(每秒 10 次到 100 次)。xApp 可以收集所需的遥测数据,执行推理并通过预先确定的控制策略集调整 vRAN 功能。不幸的是,该方案有以下严重限制:


数据量限制。 许多应用,如定位[62]、信道估算[66, 71]、干扰检测[63]和波束成形[72]都需要来自 PHY 的上行 IQ 样本。将所有 IQ 样本传送到 RIC 是不可行的(对于 100MHz 的 4×4 MIMO 来说,每个小区需要超过 5Gbps 的数据)。目前 RIC 通过在每个 xApp 服务模型中指定所需数据类型和频率(例如[37,38])来克服这一问题。数据格式及其所需的预处理(例如,子采样和平均数)取决于服务模型,vRAN 供应商必须实现和支持每个专有服务模型,因此对互操作性构成了严重限制。


实时性限制。 一些 vRAN 控制回路(如 UE 无线资源分配和功率控制)有严格的时间限制(几十𝜇s 到几 ms)。不幸的是,目前的 RIC 设计无法满足这种时间限制,预期时延>10ms[78]。与遥测的情况一样,xApps 通过使用服务模型提供的一组策略来克服这个问题,这些策略可以在 vRAN 功能内运行。然而,随着可用策略数量的增加,这种方法并不能扩展。例如,已经为网络切片提出了几种控制算法(例如,[42, 49, 52, 61, 74, 87]),每一种都是为特定情况量身定做的。将这种算法作为服务模型的一部分来实施将会非常困难,因为不得不要求所有 RAN 供应商都采用这些算法。

2.3. vRAN 可编程性的需求

基于上述的局限性,我们认为需要新的解决方案来释放 RIC 的真正能力,该解决方案应满足以下要求:


(1)提供灵活的遥测机制,受信任的开发者可以访问原始 vRAN 数据,并根据应用要求和基础设施限制选择输出数据的类型、频率和粒度。


(2)实现任意控制和推理逻辑的能力,并且可以在 RAN 内部实时运行。


(3)安全的执行环境,保证任何(受信任的)代码在 vRAN 功能内运行时不会因为执行无效的内存访问而使 vRAN 崩溃,或超出实时处理的最后期限。

3. Janus 概述

为了克服上述限制,Janus 引入了一个内联代码执行框架,允许在 vRAN 的沙盒环境中动态加载自定义遥测或控制/推理代码。

3.1. 内联代码执行框架

图 2: Janus 架构概要


图 2 显示了 Janus 的高层架构,下面介绍其主要组件。


Janus 设备(Janus device)。 Janus 设备是任何允许执行自定义代码的 vRAN 组件(即 vCU 或 vDU 进程)。Janus 在用户空间的 eBPF VM 实例内执行自定义代码[59]。我们在 vRAN 中选定的地方引入 Janus 调用点或钩子(hook) ,这些地方可以调用自定义 eBPF 代码,与 vRAN 代码内联,使 eBPF 代码可以只读访问选定的 vRAN 内部上下文和辅助函数,包括各种 3GPP 定义的数据结构(见表 1 和第 3.2 节)。自定义代码可以在运行时从 Janus 设备上动态加载和卸载,而不会影响设备性能。我们选择 eBPF 作为沙箱技术,该技术可以支持内联、快速执行,并支持用高级语言(C)编写小程序,而且提供静态代码验证。其他方法,如 Sandbox2[50]和 SAPI[51],需要在单独进程中运行自定义代码,有较高的 IPC 时延。WebAssembly[53]也是内联的,但缺乏静态验证,会导致异常内存问题[64]。

表 1: 商业级 vCU/vDU 网络功能和 OpenAirInterface 中引入的 Janus 监控钩子。


Janus 小程序(Janus codelets)。 Janus 小程序是可以在运行时动态部署在 Janus 设备上的自定义代码。开发人员用 C 语言编写小程序,使用 eBPF 编译器将其编译成字节码。与任何 eBPF 程序类似,Janus 小程序必须通过静态验证(例如,必须引入内存检查,只能有有界循环)。任何可能不安全的操作(例如,访问允许范围之外的内存),只能通过一组白名单辅助函数(helper) 来执行。小程序在两次调用之间不保留任何状态,所有状态必须存储在一个叫做 map 的外部位置。小程序通过一个特殊的 map 将遥测数据发送到设备上运行的 Janus 输出线程,后者将其转发给 Janus 控制器。小程序集(codeletset) 是一组小程序的集合,在 Janus 设备的多个钩子上运行,并通过共享 map 以非常低的延迟进行协同。如果需要,跨设备的小程序可以通过控制器协调。


Janus 控制器(Janus controller)和 SDK。 Janus 控制器负责控制 Janus 设备和小程序集,在 O-RAN 背景下,可以作为 RIC xApp 来实现。开发人员将小程序集上传到控制器,并为一个或多个 Janus 设备提供加载/卸载指令。在控制器允许加载小程序集之前,验证每个小程序集的安全性并确保其能终止。为此,我们增强了开源 PREVAIL eBPF 验证器[48],对 Janus 辅助函数和输出模式进行验证。该控制器进一步用额外的控制代码对经过验证的字节码进行处理,如果运行时间超过了某个阈值,就会强制终止(见第 5.1 节)。打过补丁的小程序被 JIT 编译并通过网络推送到 Janus 设备上,同时还有基于 protobuf 灵活定义数据输出格式所需的元数据文件(见第 5.2 节)。控制器提供数据收集器,收集并反序列化从 Janus 小程序发送的数据。Janus 还提供了 SDK,允许开发者在开发周期早期对 Janus 小程序进行本地测试,该 SDK 包括编译器、验证器和调试器,以及 Janus 设备支持的所有辅助函数和 map 定义。

3.2. vRAN RIC 新功能

我们通过一个简单而现实的例子(示例 1)来介绍 Janus 实现的新的监测和控制能力。这个例子是为 OpenAirInterface[26]的 vDU 开发的 Janus 小程序,被 FAPI 接口钩子所调用([88],图 1)。FAPI 消息是 C 结构,有发给 UE 的关于无线资源的调度信息。在这个小程序中,每隔 1000 个事件,就会有一个维护获取的 FAPI 消息数量的计数器被发送到数据采集器。虽然很简单,但这个小程序提供了重要特征,证明 Janus 比传统 RIC 的设计更强大。


 1 struct janus_load_map_def SEC (" maps ") countermap = { 2   . type = JANUS_MAP_TYPE_ARRAY , 3   . key_size = sizeof ( uint32_t ) , 4   . value_size = sizeof ( uint32_t ) , 5   . max_entries = 1 , 6 }; 7 8 struct janus_load_map_def SEC (" maps ") outmap = { 9   . type = JANUS_MAP_TYPE_RINGBUF ,10   . max_entries = 1024 ,11   . proto_msg_name = " output_msg ",12   . proto_name = " output_msg ",13   . proto_hash = PROTO_OUTPUT_MSG_HASH ,14 };1516 SEC (" janus_ran_fapi ")17 uint64_t bpf_prog ( void * state ) {18   void * c ;19   uint32_t index = 0 , counter ;20   nfapi_dl_config_request_pdu_t *p , * pend ;21   output_msg s ;2223   struct janus_ran_fapi_ctx * ctx = state ;24   p = ( nfapi_dl_config_request_pdu_t *) ctx - > data ;25   pend = ( nfapi_dl_config_request_pdu_t *) ctx - > data_end ;2627   if ( p + 1 > pend ) return 1;2829   if (p - > ndlsch_pdu > 0) {30     c = janus_map_lookup_elem (& countermap , & index ) ;31     if (! c ) return 1;32     counter = (*( int *) c + p - > ndlsch_pdu ) ;33     if ( counter == 1000) {34       s . counter = counter ;35       janus_ringbuf_output (& outmap , &s , sizeof ( s ) ) ;36       counter = 0;37     }38   }39   return 0;40 }
复制代码

示例 1: Janus 小程序示例


安全访问丰富的 vRAN 数据。 示例 1 第 17 行的状态参数是传递给 Janus 钩子的上下文,包含指向 vRAN FAPI 结构的指针41, 81。该结构含有特定下行链路时隙的调度分配信息,每个用户信息有多达 20 多个字段,包括调制和编码方案、传输块大小、分配的资源块、MIMO 等。验证器确保对内部 vRAN 上下文信息的只读访问。由于 vRAN 的模块化设计,不同标准(3GPP,Small cell 论坛)规定了少量类似接口,这些接口在 vRAN 组件中携带所有相关状态。通过在这些接口上添加钩子,可以让 Janus 开发者访问大量 vRAN 遥测数据。我们已经确定并实现了这些钩子(表 1),在第 4 节中将演示如何利用这些数据实现多个 RIC 应用,而不需要修改 vRAN 的代码。请注意,不同 vRAN 供应商对接口的实现可能有所不同(例如,不同的 C 结构内存布局)。由于 Janus 的灵活性,我们能够根据观察到的差异进行调整,通过少量代码修改来保证相同的小程序功能。


状态维护。 Janus 小程序依靠被称为 map 的共享内存区域来存储状态,并与其他小程序交换状态(参见第 4 节和附录 A.1)。Janus 提供了各种存储数据的 map 类型,包括数组、hashmap 和布隆过滤器。在这个例子中,我们使用单元素数组来维护 FAPI 数据包计数器(第 1-6 行)。每次调用时,通过辅助函数从内存中恢复计数器引用(第 30 行),根据新收到的数据包数量递增(第 32 行),同时进行各种安全检查以实现静态验证(例如第 27 行和第 31 行)。


灵活的输出格式。 Janus 小程序可以通过一个特殊类型的环形缓冲区 map(第 8-14 行),使用灵活的输出格式向数据采集器发送任意遥测数据,该 map 被关联到一个由小程序开发人员定义的特定 protobuf 格式(见第 5.2 节)。这个例子使用了一个名为output_msg的自定义 protobuf 格式(第 21 行),包含一个计数器字段(第 34 行),通过辅助函数(第 35 行)将数据导出到数据收集器。这种灵活性使我们能够基于 Janus vRAN 钩子实现 O-RAN RIC 规范中目前可用的数据模型,而无需修改 vRAN 中的任何一行代码。


安全、丰富的自定义控制操作。 Janus 小程序不能直接修改 vRAN 状态,相反,对 vRAN 行为的修改是通过由 vRAN 供应商提供的执行器辅助功能(actuator helper function) 完成的,执行器负责应用小程序决定的变更。鉴于 vRAN 功能中只有少量实时控制回路,只修改符合标准的 3GPP 参数(存在于所有 RAN 供应商的实现中),我们认为使用执行器辅助功能是合理的方式。在此基础上,我们确定并实现了一些控制钩子(列在表 2 中),这些钩子控制了大多数关键控制回路,可用于新的控制应用。我们使用切片间无线资源调度钩子作为示例,实现 OAI 中的 3 种网络切片算法(见第 4 节),通过使用allocate_slice_rbs()执行器辅助函数修改分配给每个切片的资源块数量。


表 2: 在商用级 vDU 网络功能和 OpenAirInterface 中引入 Janus 控制钩子。

4. Janus 创新用例

我们在这节介绍几个有代表性的遥测、推理和控制应用示例,说明 Janus 的价值(关于评估见第 7 节)。


表 3: Janus 的监控(M)、控制(C)、推理(I)用例,LOC 为代码行数。


灵活监控。 基于 Janus 实现的小程序可以帮助我们提取 O-RAN KPM 模型[21]中指定的 KPI(表 3 1-8 行),以及原始调度数据(9-10 行),而无需改变 vRAN 功能中的任何一行代码。这表明 Janus 有能力动态建立新的或者改变现有 O-RAN 服务模型[31, 47],无需经历漫长的标准化过程。例如,我们能够收集下行链路总物理资源块(PRB, Physical Resource Block)使用量 KPI[13],方法是利用表 1 的 Janus FAPI 钩子,并获取示例 1 中提到的nfapi_dl_config_request_pdu_t结构,其中包含每个用户调度决策分配的 PRB 数量。该结构被保存在 Janus map 中,取 0.5ms 内的平均值,并发送给 Janus 数据采集器。


低成本实时推理。 为了证明 Janus 如何克服第 2.2 节所述的数据量限制,我们开发了一个小程序集,通过将正在运行的 5G RU 转化为频谱传感器来检测外部无线干扰。小程序集由两个通过 map 进行协调的小程序组成,第一个检测没有 5G 传输时的空闲时段(挂在表 1 的 FAPI 钩子上),第二个在空闲时段对干扰进行采样(挂在表 1 的 IQ 采样钩子上)。Janus 的灵活性使我们能够根据需要指定参数调整干扰检测器的保真度和开销,比如基于哪些天线端口和 symbol 收集 IQ 样本,以什么样的频率(例如每个接收槽或每 10ms)和粒度(例如原始 IQ 样本与每个资源块平均能量比值)收集。正如第 7.2 节所示,在 vRAN 中内联执行这一推理,而不是将原始 IQ 样本导出到 RIC,能够将遥测带宽减少 40 倍。类似方法可以用来实现其他需要不同格式的无线电信道遥测数据的推理用例(例如,无线定位[62,86]和信道估算[37,38])。


此外,许多 RAN 控制回路需要实时参数预测,预测的及时性对网络性能有直接影响[28, 29, 40, 46, 66, 83, 89, 98, 100]。由于 O-RAN RIC 的延迟,xApp 只能提供 10 几毫秒前的预测,不支持实时推理[23, 77]。通过 Janus 的小程序,可以在预测延迟低于 10 毫秒的情况下在 vRAN 功能内进行推理,我们通过构建表 3 第 12-14 行所列的推理模型来验证这一功能。第一个是用于预测用户信号质量的 ARIMA 时间序列模型,采用的方法类似于[33]。第二个是用于预测信号处理任务运行时间的量化决策树,采用的是[45]的方法。更复杂的模型,如[98]中的随机森林,在 Janus C 代码中更难实现,会导致大量字节码指令(> 100K),使验证过程变得缓慢(> 20 分钟)。为了克服这一问题,我们以 map(JANUS_MAP_TYPE_ML_MODEL)的形式增强了对随机森林的支持,预先训练好的序列化随机森林模型可以被传递给 Janus,并在小程序加载过程中链接到这个 map,Janus 解析序列化的模型并验证,然后在内存中重建这一模型,小程序可以通过辅助函数janus_model_predict()访问该模型进行推理。这种方法类似于 Tensorflow 等框架为微控制器提供的序列化功能[91],并可以扩展到其他常用的 ML 模型(例如 LSTM)。关于这个过程的更多细节,请见附录 A.4。


实时控制。 许多企业应用需要网络切片以保证更严格的服务 QoS[39, 44]。现有 O-RAN 服务模型允许预先定义一组切片调度策略[34, 60, 85],以 10 秒粒度控制调度。使用 Janus,我们实现了任意调度策略的实时分片,粒度为 0.5-10ms,这在今天的 RIC 模型中是不可能的。依靠表 2 中 Janus 的片间无线资源调度钩子,由 MAC 调度器在每个调度周期开始时调用,该钩子接收基站的调度状态作为上下文(设备数量、所属切片、缓冲区大小、信号质量等)。通过这个钩子,我们用 Janus 小程序实现了三个网络切片调度器,如表 3 所列(第 15-17 行),这三个调度器都使用表 2 的allocate_slice_rbs()执行器将调度决策应用于基站。

5. 系统设计挑战

5.1. 运行时控制

现有 eBPF 验证器可以确认内存安全和终止条件,如果小程序不能有效终止(例如由于无限循环),将被拒绝执行。然而,正如第 2.3 节所提到的,当前无法对小程序在最差情况下的执行时间给予足够严格的保证。

5.1.1. 运行时间估算的挑战

估算最差情况下的执行时间的简单方法是分析小程序可以执行的最大 eBPF 指令数,这一信息可以通过对小程序最长路径的静态分析推断出来,并同时考虑有界循环的情况。然而,将指令数转化为预期运行时间是非常困难的,因为这取决于许多因素,包括 CPU 时钟、内存和缓存、eBPF 指令向 JIT 代码的转化等[36, 94]。另一个挑战是辅助函数,其执行时间在不同函数和不同参数值之间可能有很大差异。


为了说明这些挑战,请看示例 2 和 3 中的小程序。两者都执行了一个 1000 次的迭代循环,其中第一个循环调用了一个辅助函数。验证器显示,与示例 2 相比,示例 3 的小程序需要多执行 64 条指令。然而,对于参考硬件 Xeon Platinum 8168 CPU @ 2.7GHz,我们看到示例 2 小程序运行开销更大(运行时间为 4.3𝜇s,示例 3 为 2.4𝜇s)。这是因为与小程序的乘法和加法指令相比,辅助函数产生了更大的开销,表明每个小程序的最大指令数并不能很好的表示最大运行时间。


1 for (int k = 0; k < 1000; k ++) {2   index = 0;3   c = janus_map_lookup_elem (& counter , & index ) ;4   s . counter = k + 10;5 }
复制代码

示例 2: 带辅助函数的循环(平均运行时间 4.3𝜇s)


1 for ( volatile int k = 0; k < 1000; k ++) {2   counter += i ;3   counter2 = counter * i ;4   s . counter += counter2 ;5   i ++;6 }
复制代码

示例 3: 没有辅助函数的循环(平均运行时间 2.4𝜇s)

5.1.2. 通过字节码动态增强运行时

图 3: 代码修补简化流程。


为了应对这些挑战,Janus 在 eBPF 字节码中注入指令,在运行时测量小程序的执行时间,并在超过阈值时进行抢占。如图 3 所示,一个辅助函数(mark_init_time())被添加到小程序头部,将当前时间(基于 Inte rdtsc指令)存储在线程局部变量中。补丁程序在选定位置引入检查点,调用辅助函数(runtime_limit_exceeded(),图 3 第 18 行),检查自mark_init_time()以来小程序的运行时间,并将其与阈值进行比较。如果超过了阈值,小程序将被迫退出并返回错误(图 3 第 19-21 行)。运行时阈值是在加载小程序集时为每个小程序指定的(见附录 A.1 和示例 6)。最后,由于注入了指令,补丁程序需要更新所有跳转偏移量。这种方法使我们能够验证修补后的字节码的安全性,确保补丁程序所做的任何修改都不会影响小程序集的安全性。


时间检查是作为辅助函数实现的,调用了 Intel rdtsc指令,而这在 eBPF 指令集中没有对应的指令。辅助函数的调用使 eBPF 寄存器 r0-r5 失效,这些寄存器可能保存了小程序正常执行流程的状态。为了确保可验证性,Janus 存储并重新加载这些寄存器的值(图 3 第 17 和 22 行),这要求小程序在其内存栈中至少有 48 字节的存储空间(eBPF 函数有 512 字节的栈)。我们认为这是一个合理的要求,小程序总是可以使用 map 来存储更多状态。


注入点。 打补丁的关键问题是在哪里注入检查点。我们想限制两个连续检查点之间的最大指令数𝑁,以减少运行时抖动的影响(如示例 2-3 所示)。然而,每个检查点都会产生开销(调用辅助函数runtime_limit_exceeded(),保存和恢复寄存器,等等)。所有这些加起来,对于参考硬件 Xeon Platinum 8168 CPU @ 2.7GHz 来说,每个检查点开销超过 24ns。为了保持低开销,Janus 使用算法 1 分散检查点。Janus 一开始在调用被供应商标记为长效辅助函数之后添加检查点,因为如果这些函数被经常调用,可能会不安全(第 2 行)。接下来使用验证器的静态分析来穷举(从最短到最长)从小程序的第一条指令到最后一条指令的所有简单路径,以及所有循环。对于每个路径,Janus 每隔𝑁条指令添加一个检查点(第 11-14 行)。该算法考虑到了在遍历其他路径时已经添加的检查点。如果发现一个检查点,则以现有检查点为起点,对重置指令计数(第 8-9 行)。即使距离小于𝑁,每个周期也至少增加一个检查点(第 17-19 行),从而保证每隔𝑁条指令总有一个检查点。


算法 1: 检查点注入决策

数据: 𝑁 > 0,小程序指令列表𝐹,其中调用了长期辅助函数,从第一条指令到最后一条指令的所有简单小程序路径的有序列表𝑃和循环(长度增加)结果: 检查点指令位置列表𝐶 1 𝐶 ← { }; 2 foreach instruction 𝑓 in 𝐹 do 𝐶 ← 𝐶 + 𝑓; 3 foreach 𝑝 in 𝑃 do 4     ins ← 0; 5     fins ← first instruction of 𝑝; 6     foreach instruction 𝑖 in 𝑝 do 7         ins ← ins + 1; 8         if 𝑖 has already checkpoint then 9             ins ← 0;10         else11             if ins = 𝑁 then12                 𝐶 ← 𝐶 + 𝑖;13                 ins ← 0;14             end15         end16     end17     if 𝑝 is cycle and no checkpoint was added then18         𝐶 ← 𝐶 + fins;19     end20 end
复制代码


为了进行更精细的控制,Janus 允许供应商使用宏(RUNTIME_LIMIT_EXCEEDED)在长效辅助函数中设置检查点,执行与图 3 补丁类似的操作。例如,在第 4 节中讨论的随机森林模型的情况下,我们在模型的每个估算器(树)的推断后添加这样的检查。


即使是几个检查点,开销也会变得很大(例如在有紧密循环的小程序中)。为了进一步减少开销,补丁代码以抽样的频率进行检查(在𝑀个检查点中抽一个)。补丁程序在 eBPF 堆栈中增加了一个 32 位计数器,只有当这个计数器达到某个值时才进行检查(图 3 的第 15 行,右图),否则执行流程将跳回原始字节码指令,从而保证每𝑀×𝑁条指令至少进行一次检查。


抢占式控制循环。 每个控制钩子必须提供默认控制决策,如果加载的控制小程序被抢占而没有做出决策,被抢占的小程序会返回CONTROL_FAILED错误码,并执行 RAN 供应商提供的默认动作(如示例 4 所示)。例如,表 2 的切片间无线资源调度钩子的供应商默认动作可能是在切片间平均分配无线资源块。同样,对于链路适配钩子,可以设置一个强大的调制和编码方案,无论接入 UE 的信号条件如何,都能提供低错误率。最后,Janus 提供了一个辅助函数check_preemption(),允许小程序检查在上一次运行中是否被抢占,如果小程序保存了错误状态,可以进行重新设置。


1 decision = hook_custom_janus_control_operation ( ctx ) ;2 if ( decision != CONTROL_SUCCESS )3   decision = call_default_control_operation ( ctx ) ;
复制代码

示例 4: Janus 自定义控制钩子伪代码

5.2. 灵活可验证的输出格式

Janus 可以定义任意输出格式,在运行时与小程序一起加载,通过网络将输出数据传输到集中式控制器(更多细节见附录 A.2)。Janus 基于 protobufs 实现数据序列化。但是支持任意格式不利于安全性。具体来说,Janus 必须处理两个挑战。


1 message Example {2   repeated int32 element = 1;3 }4 Example.element max_count:16
复制代码

示例 5: 带有可变大小字段(最多 16 个元素)的输出格式定义示例。


首先是确保小程序不能生成任意大的可序列化消息,因为这可能不利于内存安全。Protobuf 消息由开发者定义,可以包含可变大小的字段(如重复字段或字符串)。Janus 验证器在编译时不知道消息的实际大小,因此不能静态验证。为了克服这个问题,Janus 要求在消息规范中对所有具有可变大小字段的 protobuf 定义设定一个上限,如示例 5 所示。Janus 根据消息的最大大小为小程序 C 代码分配内存,并向验证器报告(在示例中,16 × sizeof(int32) + sizeof(int16) = 66B),代价是内存消耗略有增加(在 vRAN 系统中不是瓶颈)。


其次是确保格式不正确的消息不会导致内存问题。考虑这种情况: 程序员分配了一个 30B 的内存块,作为Example的一个实例,设置 element 数量为 16,并调用 protobuf 编码器。由于内存块对于 16 个 element 来说太小了,编码器将试图从分配的内存块之外的地方进行编码,这可能会导致 segfault。为了确保内存访问安全,我们修改了验证器,以断言传递给 protobuf 编码器的内存总是等于可能的最大大小(在本例中为 66B)。像上面这样的问题仍然会造成逻辑错误,会发送乱码,但不违反安全性。

6. 实现及集成

我们在这一节提供更多关于 Janus 组件的实现及其与真实 vRAN 集成的细节。


Janus 设备(Janus device)。 Janus 设备是用 C 语言实现的,可以动态链接到 vRAN 的库。它基于 eBPF[59]的用户模式(usermode)实现,我们对其进行了扩展,以增加对 Janus map、辅助函数和输出数据机制的支持。总的来说,我们不得不在基本实现的基础上增加了 5000 行代码。开发 Janus 设备代码时没有对 vRAN 函数的线程模型做任何假设(例如,调用钩子的线程的亲和性,线程调度策略和优先级等)。然而,如果知道这些信息,Janus 可以对库实现进一步优化。我们已经非常小心确保 Janus 的快速路径(钩子可能在 vRAN 功能的时间敏感部分被调用)永远不会被阻塞或抢占。附录 A.5 中有更多关于实时优化的细节。


Janus 控制器(Janus controller)。 Janus 控制器是用 Go(数据收集器)和 Python(小程序加载器/补丁程序)编写的,有 4000 行代码。控制器通过基于 TCP 的 protobuf API 与 Janus 设备进行通信,也可以使用其他接口,如 O-RAN RIC E2 接口。对于小程序的验证,我们使用开源 PREVAIL 验证器[48],并添加了 1000 行左右的扩展代码,以增加对 Janus 特定功能的支持(即辅助函数、map 等)。最后,Janus 补丁程序依靠 pyelftools[1]和 LLVM[8]来处理小程序的 ELF 文件内容。


Janus SDK。 Janus SDK 用 Python 编写(1000 行代码),与 Janus 控制器共享部分代码库,通过 LLVM 将小程序编译成 eBPF 字节码,用 eBPF[59]将字节码转换为 x86 JIT 代码,利用 nanopb[6]为小程序编译 protobuf 输出消息格式。


vRAN 集成。 将 Janus 集成到 vRAN 非常简单快捷。为了证明这一点,我们将 Janus 设备集成到两个 vRAN 软件实现中,以此作为概念验证。一个是 CapGemini 公司[35]开发的商业级 5G vCU/vDU 实现,基于英特尔 FlexRAN PHY 设计[57]。另一个是开源 OAI[26]。两者都是用 C/C++编写的,可以很简单的集成和链接 Janus 代码。对于 Janus 的集成,我们不得不在测试的每个 vRAN 功能中增加大约 50 行初始化代码,以及为引入的每个新钩子增加大约 30 行代码。

7. 性能评估

7.1. 实验设备

软硬件配置: 为了评估 Janus 性能,我们使用了一台配备 48 个物理核心(Intel Xeon Platinum 8168 @ 2.7GHz)和 196GB 内存的服务器,禁用超线程,运行 Linux v5.15,应用了PREEMPT_RT实时补丁[82],并对实时性能进行了优化,包括禁用 P 和 C-States 以及 1GB hugepages。我们选择该配置是因为这是部署 vRAN 功能的典型配置[45, 58, 93]。


图 4: vRAN 测试平台基础设施及其性能


我们用了三套配置进行评估。第一套是端到端配置,由 CapGemini[35]的商业级 5G vRAN 堆栈组成,集成了 Janus 设备(见第 6 节),一个商业级 5G 核心网,一个 100MHz 的 4×4 富士康 RU 和 5G OnePlus Nord 智能手机(图 4a)。vRAN 基于 x86,除了 LDPC[55],所有任务都在 x86 处理器上运行。使用这种配置,我们能够产生最大 1Gbps 的下行链路和 45Mbps 的上行链路流量。Janus 基于这一配置收集 IQ 样本、FAPI 和 RLC 数据(见表 1)。在第二套配置中,我们用 RRC/F1 和 FAPI 数据的钩子,以及表 2 的切片间无线资源分配钩子对 4G OAI 进行检测。第三套也就是最后一套配置中,我们提供了一个假的 Janus 设备,这是个循环运行的单线程进程,调用连接到 Janus 钩子的小程序,我们基于这个配置进行微观测试(第 7.3 节)。


在所有配置中,Janus 钩子被线程调用,这些线程的亲和性被设置为单核,并使用SCHED_FIFO策略(不可抢占)进行调度,其调度优先级为 94。我们基于[76]的时间测量框架作为指导方针对运行时间进行测量。


vRAN 小程序时间预算: 基于 5G RAN 设置确定可以分配多少时间给 Janus 小程序,而不会影响 RAN 性能。我们专注于 vRAN DU 的 PHY 层,因为其他层对时间要求都不太严格。PHY 中数据包的传输和接收发生在固定传输时间间隔(TTI)内[45]。基于 CapGemini vRAN 设置,我们测量了 15 分钟内 4x4 MIMO 流量(1Gbps 下行和 45Mbps 上行)完全饱和时,每个 TTI 的 PHY 运行时间。图 4b 显示了上行链路和下行链路的最大运行时间与所需 CPU 核数的关系,以及基于供应商给定配置的处理期限。差值(橙色)是 Janus 小程序的最大运行时间预算,从 200𝜇s 到 600𝜇s 不等。


虽然看起时间很长,但在实践中,由于某些原因,限制要小得多。一些小程序可能在每个 TTI 中被执行多次,例如第 4 节中的 IQ 样本处理在每个 TTI 中被调用 14 次(每个 OFDM 符号一次)。此外,多个小程序可以被加载到不同的钩子上,分享整体的时间预算。最后,更高要求的 PHY 配置,如大规模 MIMO(目前无法评估),将可能给 Janus 钩子留下更少的空闲 CPU 时间。我们的设计目标是假设小程序的运行时间预算可以低至 20𝜇s。

7.2. 端到端系统评估

本节我们将展示 Janus 提取遥测数据的灵活性以及加载小程序集的安全性,来探索 Janus 在实际端到端部署中的行为和优势。对于安全部分,评估集中在第 5.1 节中介绍的运行时控制机制,Janus 控制器基于 eBPF 验证器的静态分析的有效性在[48]中得到了广泛研究。同时,可以参考表 3 的参考文献,了解我们用于实现小程序的算法性能。


我们用第 4 节介绍的干扰检测作为小程序集分析示例。我们部署 USRP 软件定义无线电作为外部干扰,产生重复的干扰模式,包括 5s 的干扰和 5s 沉默。图 5a 显示了在真实 5G 下行链路传输过程中干扰的频谱图(细尖峰)。我们在一台 OnePlus Nord 5G 手机和 5G vRAN 之间用 iperf 测量下行链路,当干扰活跃时,看到有大约 30%的丢包。测量的同时,我们加载 Janus 小程序进行干扰检测,细节在第 4 节中介绍。我们在控制器上实现了一个简单的干扰检测器,连续跟踪每个资源块的输入信号的平均值和方差,如果输入大于平均值加 3 倍标准差,则认为存在干扰。如图 5b 中所示,这种方法成功检测到了所有干扰期。


图 5: 基于 Janus 收集的数据展示的干扰和探测波谱视图。


通过补丁防止 RAN 崩溃: 因此我们接下来会展示 Janus 如何有效处理那些虽然可以通过验证,但由于执行时间长而造成 vRAN 运行安全隐患的小程序。我们为同一个实验写了另一个逻辑正确但更低效的小程序,在一个临时结构里分配 13KB 内存,在 for 循环中逐字节对内存进行 memset,然后在第二个 for 循环中逐个复制由钩子传递的 IQ 样本,并发送到控制器。


我们故意写的低效代码通过了验证,因为没有内存访问方面的安全问题,并且运行可以完结(有界循环)。然而,一旦这个小程序被加载到端到端 vRAN,就会使 vRAN 崩溃。如图 6a 中的 CDF 所示,该小程序的运行时间中位数为 51.4𝜇s,99.999 百分位为 52.2𝜇s。考虑到原始 IQ 样本钩子在每个 TTI 被调用 14 次(每个 OFDM 符号一次),小程序的平均总运行时间为 719.6𝜇s,大于 vRAN 的上行链路的 600𝜇s 时间预算(如图 4b 所示)。


图 6: 抢占非安全小程序以及基于可编程的小程序的收集数据好处。


然后,我们用 Janus 补丁程序修补小程序,并以 5𝜇s 的运行时阈值将其重新加载到 vRAN。如图 6a 所示,小程序的修补版本很早就被抢占了,因此运行时中位数现在正好变成了 5𝜇s, 99.999 百分位数变成了 5.04𝜇s。虽然修补后的小程序不再发送 IQ 样本(因为运行被抢占了),但 vRAN 受到了保护,没有违反最后期限。


减少数据采集带宽: 在相同的干扰检测示例中,两个小程序协调其输出以降低总体数据采集带宽,如第 4 节所述。为了评估协调的好处,我们还用更加集中的方式(协调发生在 RIC 中)实现相同的场景。在这种方法中,两个小程序独立将所有调度数据和原始 IQ 样本发送到控制器(每个符号约 13KB 数据),而不是在本地关联,并仅为空闲 slot 发送 IQ 样本。


我们基于这些配置测量了将输出数据发送到 Janus 收集器的吞吐量,以及两个小程序的运行时间,如图 6b 所示。在图的上半部分可以看到,原始干扰检测方法消耗了 172Mbps 的数据带宽,而基于 vRAN 内联预处理方法消耗的带宽只有 4.5Mbps,几乎减少了 40 倍。尽管有额外的预处理工作,但与原始方法相比,预处理小程序的运行时间减少了 3.5 秒。原始方法在每次小程序发送原始 IQ 样本时需要执行一次 memset 和拷贝 13KBs 的内存,而预处理方法每次调用只需要拷贝约 400B 内容。当前 O-RAN RIC 为用例指定了服务模型,并由 RAN 供应商集成,因此不可能提供自定义预处理程序。


小程序运行时。 由于篇幅所限,我们没法详细讨论第 4 节中的每个场景,但图 7 提供了表 3 中 17 个小程序的中位数和尾部(99.999)运行时间,其中小程序名使用了表 3 中的缩写,并考虑了每个小程序在最差情况下的执行情况(即最大设备数量,最大带宽等)。报告的时间基于打过补丁的小程序,我们通过补丁确保检查点距离𝑁=60 以及采样频率𝑀=10(关于参数选择细节,见第 7.3 节)。可以看到,所有小程序的运行时间都远低于 7.1 节中讨论的 20𝜇s 的时间预算(最差的小程序也小于 8𝜇s),其中要求最高的是切片调度器(SL1 和 SL3)、干扰检测(ID)和原始调度数据监测(RAW1 和 RAW2)。通过在 5G vRAN 部署中同时部署表 3 中标记为监测的所有小程序作为进一步演示,同时让网络流量达到饱和(1Gbps 下行和 45Mbps 上行),没有看到加载小程序后链路性能的任何影响。


图 7: 打过补丁后小程序的最差运行时间。

7.3. 微基准测试

图 8: 基于补丁的小程序行为分析与其他方法的比较。


补丁的开销和敏感性。 我们通过研究表 3 中对计算要求最高的小程序(即 RAW1、ID、SL1 和 SL3),根据 7.2 节的运行时间结果,探索补丁过程的行为(5.1 节)。由于篇幅所限,表 3 中其余小程序呈现出类似的修补行为,不做赘述。


首先,不同的检查点距离𝑁会引入不同的检查点数量,我们以此着手研究算法 1。正如图 8a 中看到的,小程序的指令越多(列在每个小程序标签下),引入的检查点就越多。此外,当我们增大𝑁时,检查点数量会下降。检查点数量几乎在所有情况下都略高于指令数除以𝑁,这意味着如果代码按顺序执行,有一些检查点的距离会小于𝑁。对字节码的检查显示,额外的检查点主要是在紧密循环(<𝑁条指令)中引入的,如果展开循环,就会形成一个超过𝑁个指令的代码块,这表明我们的补丁算法可以有效处理这种情况。


然后,我们研究了小程序在不同补丁距离(参数𝑁)和采样频率(参数𝑀)下的行为。图 8b 中的结果显示了未打补丁的版本与打了补丁但没有运行时间阈值的小程序运行时间比较。对于𝑁比较小的情况,运行时间开销会变得很高(比如对于 ID 来说超过了 100%),因为运行时间检查执行得非常频繁,而减少采样频率会有所帮助(如 ID 的𝑁=10 和𝑀=30 的情况所示)。另一方面,较大的𝑁值和较小的采样频率会体现为更少的运行时间检查,导致抢占式小程序的平均和尾部延迟更高,如图 8c 所示(运行时间阈值设置为 400ns)。对于𝑁=60 和𝑀=30,RAW1 和 ID 的尾部运行时间几乎比运行时间阈值多 100%。基于对表 3 中所有小程序的评估,我们发现𝑁=60 和𝑀=10 在运行时间开销和抢占延迟之间取得了最佳平衡。


最后,我们将算法 1 的检查点方法与[95, 96]中提出的另一种方法进行比较,即在被修补代码的控制流图的每个基本块上引入检查点。对于基本块方法,我们使用𝑀=30 的采样频率,在𝑁=60 和𝑀=10 的情况下,产生与 Janus 修补器相似的抢占尾部延迟结果。如图 8d 所示,与 Janus 修补器相比,基本块方法在大多数情况下的运行时间开销(99.999 尾部运行时间)会更高(例如,SL1 小程序的开销高出 2 倍以上)。开销增加的原因是,在许多情况下,基本块可能非常小(2-3 条指令),如果基本块经常被访问(热代码),那么即使使用了基于采样率的检查,检查点增加的指令也会使其运行时间增加一倍以上。Janus 采取的方法更加规范,允许 RAN 运营商或供应商选择两个检查点之间的确切指令数量。


Janus 钩子开销。 为了测量空闲 Janus 钩子的开销,我们使用假的 Janus 设备,并测量在没有加载任何小程序的情况下,在 2 百万迭代中调用一个或 10 个 Janus 钩子的耗时。表 4 列出了中位数、99.9 和 99.999 百分位数的结果。可以看到,在单个钩子调用的情况下,所有情况下的开销都可以忽略不计(<1ns)。在 10 个钩子的情况下,99.9 和 99.999 百分位数的差异上升到 10ns(每个钩子调用 1ns∼)。结论是,在 vRAN 代码中增加钩子对其性能的影响可以忽略不计。


表 4: Janus 空钩子的中位数和尾部运行时间。


数据输出开销。 接下来评估将数据复制到输出消息并将其放入输出 map 的开销(不包括输出线程和 protobuf 序列化开销)。我们以 protobuf 消息SizeMessage1为基准,定义为 protobuf 库[79]基准测试套件的一部分。这个消息总共包含 62 个字段,既有基础字段(如 int32、int64、bool),也有可变大小字段(字符串和可重复字段)。我们写了一个小程序,用随机内容和不同的消息大小来填充SizeMessage1,并将其发送出去。正如图 9a 所示,对于小数据包(<2KB),中位数和尾部运行时间都保持在 1𝜇s 以下,执行时间随着数据包大小逐渐增加,但始终保持在 2𝜇s 以下,最高达到 9KB 的大数据包。实践中,我们为第 4 节中的用例编写的小程序都不需要发送超过 2KB 的监控数据,这意味着大多数实际场景的输出开销非常低。


图 9: 小程序处理大小不同的 SizeMessage1 消息[79]的运行时间和最大 kpps。


网络开销。 最后,我们测量输出线程的开销,该线程将 protobuf 消息序列化,并通过网络将其发送给控制器。我们基于之前实验相同的配置,并测量最大可实现的数据包发送率,结果用图 9b 中的蓝线表示。对于小数据包(<500𝐵),Janus 可以在单个输出线程中序列化并发送超过 80kpps,在发送 9KB 的大数据包时,速度下降到 20kpps。根据遥测小程序(第 4 节),即使在最苛刻的情况下,单个 cell 的数据包数量和大小也落在图 9b 的橙色区域内。这意味着单个 Janus 设备可以处理多达 4 个 cell(浅蓝色和橙色区域)的苛刻用例,而对于轻量级监测,则可以处理超过一倍的 cell。目前,主要瓶颈是输出信息的序列化,可以从图 9b 的橙色线看出,因为即使我们丢弃数据包,也只看到输出速率增加了 25%,这可以通过基于 bypass kernel(例如 DPDK)的解决方案取代基于套接字的 UDP 操作来进一步优化。

8. 讨论及相关工作

向 vRAN 推送任意代码 -- [43, 73]中的工作通过在运行时在 vRAN 中加载任意代码,论证了实时 RAN 可编程性的需求。虽然这些工作在概念上与 Janus 相似,但并没有提出实现这种功能的安全方法,并承认安全问题是在真实部署中引入相关工作的障碍。他们只显示了在低端配置上的操作(高达 20MHz 的 SISO,吞吐量比我们为 Janus 展示的少 10 倍),并且没有提供对高吞吐量数据流(如 IQ 样本)的访问。


检查点补丁代码 -- 文献中研究了通过编译器辅助添加检查点,并通过定期保存软件状态来提高容错性的方法(例如,在间歇性能源系统中)[67, 68, 80, 99, 101]。在这类系统中,检查点的选择通常是以不影响可恢复性的情况下最大限度减少能耗为目标,这导致了与 Janus 的抢占目标相比不同的设计选择。与 Janus 更接近的是,[95, 96]中的工作侧重于添加检查点,以断言实时系统在最差情况下的执行是否已经超时。与 Janus 相反,这种检查需要硬件辅助,而且检查点被添加到正在运行的程序的每个基本块中,正如第 7.3 节所示,与 Janus 修补器相比,它的开销更大。


RAN 数据收集 -- vRAN 领域的一些工作提供了数据收集的解决方案,从 API 规范(例如 O-RAN RIC E2 服务模型[24, 85]和 FlexRAN API[43])到精心设计的日志系统(例如 OAI T-tracer[7],SCOPE 数据收集模块[30])。然而,这些解决方案缺乏灵活性,无法根据应用需要来调整收集数据的类型、数量和频率,而这正是 Janus 的主要设计目标之一。对于 eBPF 空间的数据收集解决方案也可以得出类似的结论,它们要么提供一套固定指标(如 Hubble[5]),要么数据只能以特定格式导出(如 ebpf_exporter[4]中的计数器和直方图)。


通过 Janus map 支持复杂 ML 模型 -- 如第 4 节所述,在 Janus C 代码中内联开发大型 ML 模型(例如,随机森林)是具有挑战性的工作,主要由于生成的字节码大小及其对验证的影响。我们相信,考虑到 RAN 的大量用例都依赖于相同模型(如随机森林、LSTM 和 RNN[18, 40, 54, 66, 84, 89, 97, 98]),我们提出的基于 map 的方法以序列化格式加载 ML 模型并通过辅助函数进行推理是非常强大的。因此,我们正计划扩展这种方法,以支持随机森林以外的其他广泛使用的 ML 模型。

9. 结论

我们在本文中提出了 Janus,一个完全可编程、安全的 5G RAN 监测和控制框架,允许运营商实时加载具有自定义数据模型的自定义小程序,大大增加了现有 O-RAN RIC 提供的灵活性。我们通过构建和评估 4 个不同类别的 17 个应用(大多数是 O-RAN RIC 无法实现的)来证明这种灵活性。Janus 使用静态验证和小程序执行预估来实现安全性,其模块化的设计使得很容易添加到现有 vRAN 产品中。我们希望 Janus 最终会被 O-RAN 社区采用,以帮助加速 Open RAN 的创新。

参考文献

[1] 2021. pyelftools. https://github.com/eliben/pyelftools.

[2] 2022. Awesome eBPF. https://github.com/zoidbergwill/awesomeebpf.

[3] 2022. eBPF. https://ebpf.io/.

[4] 2022. ebpf_exporter. https://github.com/cloudflare/ebpf_exporter.

[5] 2022. Hubble exported metrics. https://docs.cilium.io/en/stable/operations/metrics/#hubble-exported-metrics.

[6] 2022. nanopb. https://github.com/nanopb/nanopb.

[7] 2022. OAI T Tracer. https://gitlab.eurecom.fr/oai/openairinterface5g/-/wikis/T.

[8] 2022. The LLVM compiler infrastructure. https://llvm.org/.

[9] O-RAN Working Group 3. 2021. Use Cases and Requirements. ORAN.WG3.UCR-v01.00 (2021).

[10] 3GPP. 2018. 3GPP TS 38.410: NG general aspects and principles. (2018).

[11] 3GPP. 2018. 3GPP TS 38.463: E1 Application protocol (E1AP). (2018).

[12] 3GPP. 2019. 3GPP TS 38.470: F1 general aspects and principles. (2019).

[13] 3GPP. 2020. 3GPP TS 28.552: Management and orchestration: 5G performance measurements. (2020).

[14] 3GPP. 2020. 3GPP TS 32.425: Performance Management (PM); Performance measurements for Evolved Universal Terrestrial Radio Access Network (E-UTRAN). (2020).

[15] 3GPP. 2020. 3GPP TS 38.322: Radio Link Control (RLC) protocol specification. (2020).

[16] 3GPP. 2020. 3GPP TS 38.331: Radio Resource Control (RRC) protocol specification . (2020).

[17] 3GPP. 2020. 3GPP TS 38.420: Xn general aspects and principles. (2020).

[18] Javed Akhtar, Krunal Saija, Narayanan Ravi, Shekar Nethi, and Saptarshi Chaudhuri. 2021. Machine Learning-based Prediction of PMI Report for DL-Precoding in 5G-NR System. In 2021 IEEE 4th 5G World Forum (5GWF). IEEE, 105–110.

[19] ORAN Alliance. 2019. O-RAN WhitePaper-Building the Next Generation RAN. O-RAN Alliance, Tech. Rep., Oct (2019).

[20] ORAN Alliance. 2020. O-RAN use cases and deployment scenarios. White Paper, Feb (2020).

[21] ORAN Alliance. 2020. O-RAN Working Group 3: Near-Real-time RAN Intelligent Controller-E2 Service Model (E2SM). ORAN-WG3. E2SM-KPM-v01. 00.00 (2020).

[22] ORAN Alliance. 2021. O-RAN Fronthaul Control User and Synchronization Plane Specification v7.0.

[23] ORAN Alliance. 2021. O-RAN Working Group 2: “O-RAN AI/MLworkflow description and requirements 1.03. O-RAN.WG2.AIMLv01.03 Technical Specification (2021).

[24] O-RAN Alliance. 2021. O-RAN E2 Application Protocol (E2AP) v2.0. ORAN-WG3.E2AP-KPM-v02.00 (2021).

[25] O-RAN Alliance. 2021. O-RAN Minimum Viable Plan and Acceleration towards Commercialization. White Paper, June (2021).

[26] OpenAir Software Alliance. 2022. Open Air Interface Project. https://openairinterface.org/about-us/.

[27] Bharath Balasubramanian, E Scott Daniels, Matti Hiltunen, Rittwik Jana, Kaustubh Joshi, Rajarajan Sivaraj, Tuyen X Tran, and Chengwei Wang. 2021. RIC: A RAN intelligent controller platform for AIenabled cellular networks. IEEE Internet Computing 25, 2 (2021), 7–17.

[28] Andson Balieiro, Kelvin Dias, and Paulo Guarda. 2021. A Machine Learning Approach for CQI Feedback Delay in 5G and Beyond 5G Networks. In 2021 30th Wireless and Optical Communications Conference (WOCC). IEEE, 26–30.

[29] Gilberto Berardinelli, Saeed R Khosravirad, Klaus I Pedersen, Frank Frederiksen, and Preben Mogensen. 2016. Enabling early HARQ feedback in 5G networks. In 2016 IEEE 83rd Vehicular Technology Conference (VTC Spring). IEEE, 1–5.

[30] Leonardo Bonati, Salvatore D’Oro, Stefano Basagni, and Tommaso Melodia. 2021. SCOPE: an open and softwarized prototyping platform for NextG systems. In Proceedings of the 19th Annual International Conference on Mobile Systems, Applications, and Services. 415–426.

[31] Leonardo Bonati, Salvatore D’Oro, Michele Polese, Stefano Basagni, and Tommaso Melodia. 2021. Intelligence and learning in O-RAN for data-driven NextG cellular networks. IEEE Communications Magazine 59, 10 (2021), 21–27.

[32] Gabriel Brown and HEAVY READING. 2018. New Transport Network Architectures for 5G RAN. White Paper. Available online: https://www.fujitsu. com/us/Images/New-Transport-Network-Architectures-for-5GRAN. pdf (accessed on 29 June 2021) (2018).

[33] Nicola Bui and Joerg Widmer. 2018. Data-driven evaluation of anticipatory networking in LTE networks. IEEE Transactions on Mobile Computing 17, 10 (2018), 2252–2265.

[34] Cambridge Consultants. 2022. Wireless breakthrough for the Ocado Smart Platform. https://www.cambridgeconsultants.com/case-studies/wireless-breakthrough-ocado-smart-platform.

[35] CapGemini Engineering. 2022. 5G gNodeB. https://capgeminiengineering.com/nl/en/services/next-core/wireless-frameworks/.

[36] Francisco J Cazorla, Leonidas Kosmidis, Enrico Mezzetti, Carles Hernandez, Jaume Abella, and Tullio Vardanega. 2019. Probabilistic worst-case timing analysis: Taxonomy and comprehensive survey. ACM Computing Surveys (CSUR) 52, 1 (2019), 1–35.

[37] Cellwize and Intel. 2022. Cellwize Announces Collaboration to Accelerate Deployment of 5G vRAN Networks With AI. https://www.sdxcentral.com/articles/press-release/cellwizeannounces-collaboration-to-accelerate-deployment-of-5g-vrannetworks-with-ai/2021/06/.

[38] Cohere Technologies. 2022. With Vodafone and Partners, VMWare demonstrates how to accelerate innovation in the RAN. https://www.cohere-tech.com/press-releases/with-vodafone-and-partnersvmware-demonstrates-how-to-accelerate-innovation-in-the-ran.

[39] Salah Eddine Elayoubi, Sana Ben Jemaa, Zwi Altman, and Ana Galindo-Serrano. 2019. 5G RAN slicing for verticals: Enablers and challenges. IEEE Communications Magazine 57, 1 (2019), 28–34.

[40] Capgemini Engineering. 2021. Intelligent 5G L2 MAC Scheduler. White Paper, Feb (2021).

[41] Small Cell Forum. 2021. 5G FAPI: PHY API Specification.

[42] Xenofon Foukas, Mahesh K Marina, and Kimon Kontovasilis. 2019. Iris: Deep reinforcement learning driven shared spectrum access architecture for indoor neutral-host small cells. IEEE Journal on Selected Areas in Communications 37, 8 (2019), 1820–1837.

[43] Xenofon Foukas, Navid Nikaein, Mohamed M Kassem, Mahesh K Marina, and Kimon Kontovasilis. 2016. FlexRAN: A flexible and programmable platform for software-defined radio access networks. In Proceedings of the 12th International on Conference on emerging Networking EXperiments and Technologies. 427–441.

[44] Xenofon Foukas, Georgios Patounas, Ahmed Elmokashfi, and Mahesh K Marina. 2017. Network slicing in 5G: Survey and challenges. IEEE communications magazine 55, 5 (2017), 94–100.

[45] Xenofon Foukas and Bozidar Radunovic. 2021. Concordia: teaching the 5G vRAN to share compute. In Proceedings of the 2021 ACM SIGCOMM 2021 Conference. 580–596.

[46] Gines Garcia-Aviles, Andres Garcia-Saavedra, Marco Gramaglia, Xavier Costa-Perez, Pablo Serrano, and Albert Banchs. 2021. Nuberu: Reliable RAN virtualization in shared platforms. In Proceedings of the 27th Annual International Conference on Mobile Computing and Networking. 749–761.

[47] Andres Garcia-Saavedra and Xavier Costa-Perez. 2021. O-RAN: Disrupting the virtualized RAN ecosystem. IEEE Communications Standards Magazine (2021).

[48] Elazar Gershuni, Nadav Amit, Arie Gurfinkel, Nina Narodytska, Jorge A Navas, Noam Rinetzky, Leonid Ryzhyk, and Mooly Sagiv. 2019. Simple and precise static analysis of untrusted linux kernel extensions. In Proceedings of the 40th ACM SIGPLAN Conference on Programming Language Design and Implementation. 1069–1084.

[49] David Ginthör, René Guillaume, Maximilian Schüngel, and Hans D Schotten. 2021. 5G RAN slicing for deterministic traffic. In 2021 IEEE Wireless Communications and Networking Conference (WCNC). IEEE, 1–6.

[50] Google. 2022. Sandbox2. https://developers.google.com/codesandboxing/sandbox2.

[51] Google. 2022. Sandboxed API. https://developers.google.com/codesandboxing/sandboxed-api.

[52] Tao Guo and Alberto Suárez. 2019. Enabling 5G RAN slicing with EDF slice scheduling. IEEE Transactions on Vehicular Technology 68, 3 (2019), 2865–2877.

[53] Andreas Haas, Andreas Rossberg, Derek L Schuff, Ben L Titzer, Michael Holman, Dan Gohman, Luke Wagner, Alon Zakai, and JF Bastien. 2017. Bringing the web up to speed with WebAssembly. In Proceedings of the 38th ACM SIGPLAN Conference on Programming Language Design and Implementation. 185–200.

[54] Sahar Imtiaz, Georgios P Koudouridis, Hadi Ghauch, and James Gross. 2018. Random forests for resource allocation in 5G cloud radio access networks based on position information. EURASIP Journal on Wireless Communications and Networking 2018, 1 (2018), 1–16.

[55] Intel. 2020. Unleash the Speed of 4G and 5G Virtualized Radio Access Networks (vRAN). Product Brief, Intel vRAN Dedicated Accelerator ACC100 (2020).

[56] Intel. 2020. Virtual RAN (vRAN) with Hardware Acceleration. White Paper, Jan (2020).

[57] Intel. 2022. FlexRAN Reference Architecture for Wireless Access. https://www.intel.com/content/www/us/en/developer/topictechnology/edge-5g/tools/flexran.html.

[58] Intel. 2022. Smart Edge Open Radio Access Network.https://smart-edge-open.github.io/ido-specs/doc/referencearchitectures/ran/smartedge-open_ran/.

[59] iovisor. 2022. Userspace eBPF VM. https://github.com/iovisor/ubpf.

[60] David Johnson, Dustin Maas, and Jacobus Van Der Merwe. 2022. NexRAN: Closed-loop RAN slicing in POWDER-A top-to-bottom open-source open-RAN use case. In Proceedings of the 15th ACM Workshop on Wireless Network Testbeds, Experimental evaluation & CHaracterization. 17–23.

[61] Ravi Kokku, Rajesh Mahindra, Honghai Zhang, and Sampath Rangarajan. 2011. NVS: A substrate for virtualizing wireless resources in cellular networks. IEEE/ACM transactions on networking 20, 5 (2011), 1333–1346.

[62] Manikanta Kotaru, Kiran Joshi, Dinesh Bharadia, and Sachin Katti. 2015. Spotfi: Decimeter level localization using wifi. In Proceedings of the 2015 ACM Conference on Special Interest Group on Data Communication. 269–282.

[63] Merima Kulin, Tarik Kazaz, Ingrid Moerman, and Eli De Poorter. 2018. End-to-end learning from spectrum data: A deep learning approach for wireless signal identification in spectrum monitoring applications. IEEE Access 6 (2018), 18484–18501.

[64] Daniel Lehmann, Johannes Kinder, and Michael Pradel. 2020. Everything Old is New Again: Binary Security of {WebAssembly}. In 29th USENIX Security Symposium (USENIX Security 20). 217–234.

[65] liburcu. 2022. Userspace RCU. https://liburcu.org/.

[66] Changqing Luo, Jinlong Ji, Qianlong Wang, Xuhui Chen, and Pan Li. 2018. Channel state information prediction for 5G wireless communications: A deep learning approach. IEEE Transactions on Network Science and Engineering 7, 1 (2018), 227–236.

[67] Kiwan Maeng, Alexei Colin, and Brandon Lucia. 2017. Alpaca: Intermittent execution without checkpoints. Proceedings of the ACM on Programming Languages 1, OOPSLA (2017), 1–30.

[68] Kiwan Maeng and Brandon Lucia. 2018. Adaptive dynamic checkpointing for safe efficient intermittent computing. In 13th USENIX Symposium on Operating Systems Design and Implementation (OSDI 18). 129–144.

[69] Paul E McKenney, Silas Boyd-Wickizer, and Jonathan Walpole. 2013. RCU usage in the linux kernel: One decade later. Technical report (2013).

[70] Paul E McKenney and Jonathan Walpole. 2007. What is RCU, fundamentally? Linux Weekly News (LWN. net) (2007).

[71] Mehrtash Mehrabi, Mostafa Mohammadkarimi, Masoud Ardakani, and Yindi Jing. 2019. Decision Directed Channel Estimation Based on Deep Neural Network 𝑘-Step Predictor for MIMO Communications in 5G. IEEE Journal on Selected Areas in Communications 37, 11 (2019), 2443–2456.

[72] Mustafa Mohsin, Jordi Mongay Batalla, Evangelos Pallis, George Mastorakis, Evangelos K Markakis, and Constandinos X Mavromoustakis. 2021. On Analyzing Beamforming Implementation in O-RAN 5G. Electronics 10, 17 (2021), 2162.

[73] Navid Nikaein, Chia-Yu Chang, and Konstantinos Alexandris. 2018. Mosaic5G: Agile and flexible service platforms for 5G research. ACM SIGCOMM Computer Communication Review 48, 3 (2018), 29–34.

[74] Daisuke Nojima, Yuki Katsumata, Takuya Shimojo, Yoshifumi Morihiro, Takahiro Asai, Akira Yamada, and Shigeru Iwashina. 2018. Resource isolation in RAN part while utilizing ordinary scheduling algorithm for network slicing. In 2018 IEEE 87th Vehicular Technology Conference (VTC Spring). IEEE, 1–5.

[75] O-RAN SC projects . 2022. RAN Intelligent Controller Applications. https://docs.o-ran-sc.org/en/latest/projects.html#ranintelligent-controller-applications-ricapp.

[76] Gabriele Paoloni. 2010. How to benchmark code execution times on Intel IA-32 and IA-64 instruction set architectures. Intel Corporation 123 (2010), 170.

[77] Michele Polese, Leonardo Bonati, Salvatore D’Oro, Stefano Basagni, and Tommaso Melodia. 2022. Understanding O-RAN: Architecture, Interfaces, Algorithms, Security, and Research Challenges. arXiv preprint arXiv:2202.01032 (2022).

[78] Michele Polese, Rittwik Jana, Velin Kounev, Ke Zhang, Supratim Deb, and Michele Zorzi. 2020. Machine learning at the edge: A datadriven architecture with applications to 5G cellular networks. IEEE Transactions on Mobile Computing 20, 12 (2020), 3367–3382.

[79] Protocol Buffers. 2022. Protobuf benchmark proto file. https://github.com/protocolbuffers/protobuf/blob/fb77cc9d9f066a8ce4f12e8d5f76188d48101444/benchmarks/google_size.proto.

[80] Benjamin Ransford, Jacob Sorber, and Kevin Fu. 2011. Mementos: System support for long-running computation on RFID-scale devices. In Proceedings of the sixteenth international conference on Architectural support for programming languages and operating systems. 159–170.

[81] Raymond Knopp. 2022. OAI Layer 2 Protocol Stack. https://www.openairinterface.org/docs/workshop/1stOAINorthAmericaWorkshop/Training/KNOPP-OAI-L2.pdf.

[82] Rohde & Schwarz. 2022. PREEMPT_RT patch versions. https://www.rohde-schwarz.com/uk/solutions/aerospace-defensesecurity/security/spectrum-monitoring/efficient-interferencehunting/huntinginterferences_91389.html.

[83] Peter Rost and Athul Prasad. 2014. Opportunistic hybridARQ—Enabler of centralized-RAN over nonideal backhaul. IEEEWireless Communications Letters 3, 5 (2014), 481–484.

[84] Krunal Saija, Shekar Nethi, Saptarshi Chaudhuri, and RM Karthik. 2019. A machine learning approach for SNR prediction in 5G systems. In 2019 IEEE International Conference on Advanced Networks and Telecommunications Systems (ANTS). IEEE, 1–6.

[85] Robert Schmidt, Mikel Irazabal, and Navid Nikaein. 2021. FlexRIC: an SDK for next-generation SD-RANs. In Proceedings of the 17th International Conference on emerging Networking EXperiments and Technologies. 411–425.

[86] Souvik Sen, Božidar Radunovic, Romit Roy Choudhury, and Tom Minka. 2012. You are facing the Mona Lisa: Spot localization using PHY layer information. In Proceedings of the 10th international conference on Mobile systems, applications, and services. 183–196.

[87] Weisen Shi, Junling Li, Peng Yang, Qiang Ye, Weihua Zhuang, Xuemin Shen, and Xu Li. 2021. Two-level soft RAN slicing for customized services in 5G-and-beyond wireless communications. IEEE Transactions on Industrial Informatics 18, 6 (2021), 4169–4179.

[88] Small Cell Forum. 2022. 5G FAPI: PHY API Specification. http://scf.io/en/documents/222_5G_FAPI_PHY_API_Specification.php.

[89] Nils Strodthoff, Barış Göktepe, Thomas Schierl, Cornelius Hellge, and Wojciech Samek. 2019. Enhanced machine learning techniques for early HARQ feedback prediction in 5G. IEEE Journal on Selected Areas in Communications 37, 11 (2019), 2573–2587.

[90] Telefonica. 2021. Telefonica views on the design, architecture, and technology of 4G/5G Open RAN networks. White Paper, Jan (2021).

[91] TensorFlow. 2022. TensorFlow Lite for Microcontrollers. https://www.tensorflow.org/lite/microcontrollers.

[92] Marcos AM Vieira, Matheus S Castanho, Racyus DG Pacífico, Elerson RS Santos, Eduardo PM Câmara Júnior, and Luiz FM Vieira. 2020. Fast packet processing with ebpf and xdp: Concepts, code, challenges, and applications. ACM Computing Surveys (CSUR) 53, 1 (2020), 1–36.

[93] OpenAirInterface Wiki. 2022. OpenAirKernelMainSetup. https://gitlab.eurecom.fr/oai/openairinterface5g/-/wikis/OpenAirKernelMainSetup.

[94] Reinhard Wilhelm, Jakob Engblom, Andreas Ermedahl, Niklas Holsti, Stephan Thesing, David Whalley, Guillem Bernat, Christian Ferdinand, Reinhold Heckmann, Tulika Mitra, et al. 2008. The worst-case execution-time problem—overview of methods and survey of tools. ACM Transactions on Embedded Computing Systems (TECS) 7, 3 (2008), 1–53.

[95] Julian Wolf, Bernhard Fechner, Sascha Uhrig, and Theo Ungerer. 2012. Fine-grained timing and control flow error checking for hard real-time task execution. In 7th IEEE International Symposium on Industrial Embedded Systems (SIES’12). IEEE, 257–266.

[96] Julian Wolf, Bernhard Fechner, and Theo Ungerer. 2012. Fault coverage of a timing and control flow checker for hard real-time systems. In 2012 IEEE 18th International On-Line Testing Symposium (IOLTS). IEEE, 127–129.

[97] Hao Yin, Xiaojun Guo, Pengyu Liu, Xiaojun Hei, and Yayu Gao. 2020. Predicting Channel Quality Indicators for 5G Downlink Scheduling in a Deep Learning Approach. arXiv preprint arXiv:2008.01000 (2020).

[98] Qi Zhang, Alexandros Nikou, and Marios Daoutis. 2022. Predicting Buffer Status Report (BSR) for 6G Scheduling using Machine Learning Models. In 2022 IEEE Wireless Communications and Networking Conference (WCNC). IEEE, 632–637.

[99] Ying Zhang and Krishnendu Chakrabarty. 2003. Energy-aware adaptive checkpointing in embedded real-time systems. In 2003 Design, Automation and Test in Europe Conference and Exhibition. IEEE, 918–923.

[100] Yadan Zheng, Shubo Ren, Xiaoyan Xu, Ying Si, Mingke Dong, and Jianjun Wu. 2012. A modified ARIMA model for CQI prediction in LTE-based mobile satellite communications. In 2012 IEEE International Conference on Information Science and Technology. IEEE, 822–826.

[101] Avi Ziv and Jehoshua Bruck. 1997. An on-line algorithm for checkpoint placement. IEEE Transactions on computers 46, 9 (1997), 976–985.

附录

附录.1 加载 Janus 小程序集及小程序调度

正如第 3.1 节所解释的,Janus 小程序通过 Janus 控制器提供的网络 API 进行 JIT 编译并加载到 Janus 设备上。开发者可以使用 Janus SDK 提供的工具将开发的小程序上传到 Janus 控制器并加载到 Janus 设备,如图 10 所示。将小程序上传到 Janus 控制器并加载到 Janus 设备所需的指令被编码在一个以 YAML 格式编写的描述符文件中,其结构和属性在示例 6 中列出。


 1 codelet1: 2   codelet: codelet1.o 3   hook_name: hook_name1 4   priority: codelet1_running_priority 5   runtime_threshold: codelet1_max_runtime 6 codeletN: 7   codelet: codeletN.o 8   hook_name: hook_nameN 9   priority: codeletN_running_priority10   runtime_threshold: codeletN_max_runtime11   linked_maps:12     codeletN_map:13       codelet: codelet114       map_name: codelet1_map
复制代码

示例 6: 小程序 YAML 格式


YAML 文件指定了小程序集中所有小程序的名称(ELF 格式的 eBPF 字节码对象文件),被链接到 Janus 设备中的钩子名称以及调度优先级(多个小程序可以被链接到同一个钩子)。YAML 文件为进一步配置小程序提供了额外的可选配置参数,例如,在利用 5.1 节的运行时控制机制时,为每个打补丁的小程序设置运行时阈值。


图 10: 将小程序加载到 Janus 设备的过程。


同一小程序集的小程序可以共享状态并协调执行,这在执行监测或控制操作时特别有用,这些操作需要获取跨 vRAN 堆栈不同层的事件和数据(例如,在第 4 节干扰检测的情况下)。小程序之间的状态共享是通过共享 map 实现的,为了使这种机制发挥作用,想要共享状态的小程序必须在其typekey_sizevalue_sizemax_entries方面使用完全相同的共享 map 定义,而 map 名称可以不同。然后,开发者可以在用于加载小程序集的 YAML 描述符文件的linked_maps部分指定要链接的 map,如示例 6 所示。当小程序集被加载时,共享 map 的内存在 Janus 设备上只被分配一次,所有共享 map 的小程序都会得到一个指向相同内存的指针,然后可以通过辅助函数调用该内存来存储和加载状态。

附录.2 灵活的 Janus 输出格式

输出格式可以被多个小程序复用。通过 Janus SDK,输出格式定义和小程序被分别上传到 Janus 控制器,小程序在其环形输出缓冲区 map 的定义中指定使用哪种输出格式,包括三个字段,如示例 1 的第 11-13 行所示。proto_name字段包含名称,表示已经上传到 Janus 控制器的唯一的 protobuf 规范文件。proto_msg_name字段表示proto_name规范的根消息,用于通过这个环形缓冲区发送数据(一个 proto 规范可以包含多个消息定义)。最后,proto_hash字段包含哈希值,用来确保开发小程序时使用的 protobuf 规范文件的内容与上传到 Janus 控制器的文件内容相同。


图 11: 将带有输出格式定义的 Janus 小程序集加载到 Janus 设备的过程。


图 11 说明了带有输出格式定义的小程序集的加载过程。Janus 控制器解析小程序对象(ELF)文件,识别 map 部分中JANUS_MAP_TYPE_RINGBUF类型,然后基于 map 定义中的proto_name值,将小程序与先前上传到控制器的一些.proto规范文件联系起来。一旦找到规范定义,控制器将 map 的proto_hash字段与.proto文件的哈希值进行比较。如果匹配,控制器会给小程序的环形缓冲区 map 分配唯一的 stream-id(一个 16 字节的 UUID)。接下来,控制器自动生成编码器(encoder)解码器(decoder) 函数,负责对小程序发送至 Janus 输出数据收集器的proto_msg_name类型的消息进行序列化和反序列化。控制器通过网络 API 将自动生成的编码器函数与经过验证的小程序字节码和输出 map 的 stream-id 一起发送到 Janus 设备。控制器还将 stream-id 与自动生成的解码器函数一起发送给输出数据收集器。收集器维护一个键值结构,将 stream-id(键)映射到解码器函数(值)。


每次有JANUS_MAP_TYPE_RINGBUF类型输出 map 的小程序被加载到 Janus 设备上,一个单生产者/单消费者(SPSC)的环形缓冲区数据结构就会被创建并链接,其中小程序是生产者,输出线程是消费者。如图 12 所示,每次小程序调用janus_ringbuf_output()辅助函数(例如示例 1 的第 42 行),输出数据就被推送到环形缓冲区。输出线程消费这些数据,并调用相应的编码器函数对其进行序列化。在通过 UDP 将序列化数据发送到输出收集器之前,会附加一个头域,其中包括 16 字节的 stream-id 和 2 字节的序列号。一旦输出收集器收到输出信息,就会将 stream-id 与对应的解码器函数相匹配,用来反序列化该信息。最后,反序列化的消息被转换为 JSON 格式,然后可以被输送到流水线上的其他组件(如存储、ML 处理等)。


图 12: Janus 小程序输出数据。

附录.3 编写 Janus 钩子函数

为了简化编写 Janus 钩子的过程,Janus SDK 提供了一套用于声明和运行新钩子的宏。简而言之,调用DECLARE_JANUS_HOOK()宏,并将新钩子的名称、传递给钩子的小程序上下文类型、钩子函数签名(名称和参数类型)以及用于填充将被传递给小程序的上下文赋值列表作为输入参数。示例 7 是示例 1 中小程序的钩子示例。


 1 DECLARE_JANUS_HOOK(fapi_dl_config_req , 2         struct janus_ran_fapi_ctx ctx , 3         ctx , 4         HOOK_PROTO ( 5             nfapi_dl_config_request_pdu_t * dl_config_req , 6             int ctx_id , 7             int frame , 8             int subframe , 9             int cell_id ,10             int fapi_list_size11             ) ,12         HOOK_ASSIGN (13             ctx.ctx_id = ctx_id ;14             ctx.cell_id = cell_id ;15             ctx.slot = subframe ;16             ctx.frame = frame ;17             ctx.data = ( void *) dl_config_req ;18             ctx.data_end = ( void *) ( dl_config_req + fapi_list_size ) ;19             )20         )
复制代码

示例 7: 示例 1 中小程序的钩子定义


基于这些输入,宏会自动生成构成钩子 API 的函数模板代码,包括钩子加载和卸载小程序的函数,以及运行与钩子链接的所有小程序的函数。表 5 显示了示例 7 自动生成的函数列表。


表 5: 示例 7 中通过DECLARE_JANUS_HOOK()宏自动生成的函数


一旦声明了钩子,开发者可以通过DEFINE_JANUS_HOOK()这个宏来实例化钩子,将钩子名称作为参数传入 vCU/vDU 代码中。最后,通过调用自动生成的函数hook_#hook_name(),可以在代码的任何地方调用该钩子,其中#hook_name是声明该钩子时使用的名称。例如,在示例 7 中,会生成钩子hook_fapi_dl_config_req()

附录.4 基于 Janus 进行推理

接下来我们详细解释 Janus 如何通过 map 使用更复杂的 ML 模型进行推理。示例 8 中显示了一个简单的小程序例子,用于第 4 节中讨论的随机森林模型。这个小程序对一个预先训练好的模型进行推理,然后返回。


 1 struct janus_load_map_def SEC("maps") model_map = { 2   .type = JANUS_MAP_TYPE_ML_MODEL , 3   .max_entries = 16 , 4   .ml_model = "random_forest", 5 }; 6 7 struct features { 8   int f1 ; 9   int f2 ;10   int f3 ;11   int o1 ;12 };1314 SEC("janus_ran_fapi")15 uint64_t bpf_prog(void *state) {1617   struct features feats ;18   int res ;1920   feats.f1 = 1;21   feats.f2 = 1;22   feats.f3 = 1;2324   /* We store inference result in output */25   res = janus_model_predict(&model_map , &feats);2627   if (res) return 1;2829   return 0;30 }
复制代码

示例 8: ML 模型使用示例


加载 ML 模型 -- 从示例 8 第 2 行可以看出,我们定义了一个JANUS_MAP_TYPE_ML_MODEL类型的 map,该模型必须由控制器以序列化格式从一个名为random_forest的输入文件中加载(第 4 行)。序列化的模型以 char 数组的形式表示,并获取 janus 所需的所有重要信息,以便在内存中重新创建训练好的模型。例如,对于随机森林模型,序列化包含关于模型类型(随机森林)、估算器(树)数量、对每个估算器的每个节点进行检查的条件以及树的叶子节点的推理值等信息。Janus 只支持一组预先确定的模型类型(目前是随机森林和 SVM),每个模型都有自己的序列化参数集。在加载小程序的过程中,验证器将检查加载的序列化模型是否有效,包括检查模型类型以及模型参数的有效性(即模型是否可以在内存中重构)。如果任何一项检查失败,那么小程序就不会被加载到 Janus 设备中。


程序内推理 -- 加载的模型希望有一组输入特征以及确定数量和大小的输出,输入特征和输出所需的内存在 ML 模型 map 定义中指定。比如示例 8 有 3 个输入特征和 1 个输出(第 7-12 行),总内存大小为 16 字节(第 3 行)。输入特征和输出的确切内存布局取决于训练好的模型,因此是由小程序决定的。有了输入特征,可以通过调用辅助函数janus_model_predict()进行推理,如第 25 行所示。

附录.5 实时运算

还有更多为 Janus 所作的优化的细节,以确保实时性能:


输出 map -- 对于每个输出流,创建一个无锁的单生产者/单消费者环形缓冲区,将数据从小程序推送到输出线程,避免任何系统调用(见图 2)。这确保了小程序永远不会被抢占,并且在最坏情况下可能只是丢掉多余的数据包。


内存分配 -- Janus 使用预先分配的内存进行操作(加载小程序的 JIT 代码,map,数据输出等)。它依赖 DPDK mempools 和 Mbufs 在无锁模式下运行(使用rte_stack mempool),从而确保使用同一 mempool 的多个线程在被抢占的情况下不会影响其他线程的性能,并且最小化在 fastpath 中访问内存的抖动。


Janus map 的并发性 -- 根据设计,Janus map 不使用锁,以保证时间敏感的 vRAN 功能的实时性能,因此是非线程安全的,并可能会导致并发性问题(例如,在多实例工作线程代码中调用钩子)。然而,根据我们使用商业级 vRAN 功能的 Janus 的经验,大多数情况下,只要某种上下文 ID 作为钩子上下文的一部分被传递,以识别哪个实例正在调用钩子(例如,哪个 CPU 核心,哪个工作线程等),就可以用无锁的方式编写小程序。我们正计划在未来适当的时候通过采用线程安全的 map 解决这一限制。


加载/卸载小程序 -- 我们通过基于用户空间实现的 RCU(Read-Copy-Update)[65]将小程序加载(卸载)到 Janus 钩子上。RCU 可以实现无锁访问共享数据结构,代价是写入/更新时间[69, 70]更长。这对 Janus 很适合,执行小程序的快速 vRAN 线程会读取数据,而更新钩子小程序列表的(非实时)线程写入/更新该数据。




你好,我是俞凡,在 Motorola 做过研发,现在在 Mavenir 做技术工作,对通信、网络、后端架构、云原生、DevOps、CICD、区块链、AI 等技术始终保持着浓厚的兴趣,平时喜欢阅读、思考,相信持续学习、终身成长,欢迎一起交流学习。

微信公众号:DeepNoMind

发布于: 刚刚阅读数: 3
用户头像

俞凡

关注

公众号:DeepNoMind 2017-10-18 加入

俞凡,Mavenir Systems研发总监,关注高可用架构、高性能服务、5G、人工智能、区块链、DevOps、Agile等。公众号:DeepNoMind

评论

发布
暂无评论
Janus: 基于eBPF的5G实时AI控制器_架构_俞凡_InfoQ写作社区