VPP(2):软件架构,VPP-infra,VLIB

VPP软件架构

VPP软件从下至上分为VPP infra, VLIB, VNET, Plugins四层。

报文处理图

VPP-Infra

VPP基础设施层。是一个基础服务集合。提供内存访问,向量、环、哈希表等数据结构接口,以及报文处理图节点、定时器等。VPP infra已经完成近20年,不会有经常的变更。包含:

  • 向量
  • 位图
  • 池:结合向量和位图,以便于快速分配定长的数据结构
  • 哈希表
  • 定时器
  • 单调时钟
  • 字符串format,unformat

VLIB

矢量处理库。vlib层处理各种应用程序管理功能:缓存、内存和报文处理图节点管理。维护计数器,轻量级的多任务线程,数据包跟踪。并实现了CLI。main函数也在此层。

初始化

使用 VLIB_INIT_FUNCTION (my_init_function) macros宏来定义初始化函数。默认情况下,所有初始化函数的执行顺序不定。

可以通过以下手段来约束初始化函数的执行顺序:

1
2
3
4
5
6

VLIB_INIT_FUNCTION(my_init_function) =
{
.runs_before = VLIB_INITS("we_run_before_function_1", "we_run_before_function_2"),
.runs_after = VLIB_INITS("we_run_after_function_1", "we_run_after_function_2),
};

报文处理图初始化

报文处理图定义了一系列的图节点用于处理报文。框架支持在运行时往图中添加节点,不支持移除节点。vlib提供了多种类型的节点,按分发行为来分类(vlib_node_registration_t ):

  • VLIB_NODE_TYPE_PRE_INPUT:在其它节点类型之前执行
  • VLIB_NODE_TYPE_INPUT:在pre_input节点之后,尽快执行
  • VLIB_NODE_TYPE_INTERNAL:只在针对挂起的报文,显式配置运行态时执行。
  • VLIB_NODE_TYPE_PROCESS:只在显式配置运行态时执行,在多任务线程中执行。节点会在挂起一段时间后被执行。

报文处理图节点分发

报文处理图节点分发的函数入口是:./src/vlib/main.c:vlib_main_loop.。报文分发的流程很简单,但是可能会很难理解:分发器将向量发入处理图中,如果需要的话,把它切分成更小的向量,直至原始向量中的所有工作都被处理完。

这一方案需要在向量中的报文个数上做一个权衡:如果向量中的报文个数增加,每个报文的处理时间减小。是因为:节点处理的第一个分片报文的处理过程中,把处理所需的指令加载到L1 I-cache中,后续所有报文都会此因受益,可以使用I-cache中已经加载好的指令。

参考资料