P4基础理论
P4基础理论
P4架构
图片来自官方P4_tutorial.pptx 中,7-21页内容
自底向上的设计使得灵活的网络需求无法下发给交换机,所以更好的方法是自顶向下的设计,用户/控制器确定规则。我们真正想要的是,能够在high-level上精确定义芯片应该如何处理数据包(通过编写p4程序实现)
P4基于高速的包处理设备的抽象模型,称为PISA,代表协议无关的交换机架构(Protocol-Independent Switch Architecture),主要包括三个部分:
- parser:用于解析数据包,生成独立的数据包头与中间信息
- match-action pipeline:用于定义table和准确的处理算法
- deparser:用于声明输出数据包的格式
parser被建模为一个简单的、确定性的状态机,它通常根据事先指定的包头中,特定字段的值进行状态间的跳转;match-action pipeline是PISA架构的核心,可以将一些数据与对应的表(包含一些entry)进行匹配,并进行相应的action;deparser与parser相反,它重新组装数据包,数据包重新被序列化
P4 Target:特定的硬件实现
P4 Architecture:通过一组P4可编程、外部(externs)与固定组件,提供对P4 Target进行编程的接口
除了V1Model,目前还有Portable Switch Architecture和Tofino native等架构,其中tofino native的架构比v1model有更多的功能,PSA的架构可以被更多的target (FPGA,ASIC,Software)所支持
可以按照v1model的架构来写程序,之后compiler会帮助把v1model的程序转换成其他的架构的程序
对一个P4 target编写P4程序的过程,由几个部分构成:
- 用户提供:P4程序与控制平面
- 厂家提供:P4架构模型,编译器,目标硬件
- runtime:添加/删除流表,外部控制(这两个是从控制平面到数据平面),数据包信息上报控制面(从数据平面到控制平面)
V1Model架构包括5个部分:
- Parser:解析器,对数据包根据预先定义好的格式进行解析,并提取头部的各个字段
- Ingress:Ingress流水线部分,数据处理逻辑的入口
- TM:Traffic Manager,定义核心的处理逻辑
- Egress:Egress流水线部分,数据处理逻辑的出口
- Deparser:对数据包进行重组
P4基础语法
官方P4_tutorial.pptx 中,22-47页讨论了这部分内容
P4-16代码模板如图所示:
数据类型
basic types:
bit <n>
:n位的无符号整型(bitstring)bit
:等价于bit <1>
int <n>
:n(n >=2)位的有符号整型varbit <n>
:最大为n位的,变长bitstring
header types:是members的有序集合,其成员的类型可以是bit<n>
、int<n>
和varbit<n>
header类型的注意事项:
- 长度需要字节对齐,即长度必须是8bit的整数倍
- header可以是有效的(valid)或者无效的(invalid),可以使用
isValid()
测试有效位,用setValid()
和setInvalid()
设置有效位
typedef
:为type设置别名,例如typedef bit<32> ip4Addr_t;
struct:是无序的数据类型集合,且不需要字节对齐,可用于组织元数据,例如struct standard_metadata_t
header stack:一组header(可看作数组形式);header union:是header的集合,只能使用其中一个
parser部分
parser类似于C语言中的函数(允许循环),通过一系列状态(state)的执行与转换,提取报头字段与元数据
每个parser都有三个预设状态,其他状态可由用户自行定义:
start
:进入parser
功能块后的第一个状态,自动进入accept
:进入accept
状态,则表示数据报进入后续control流程reject
:数据包被丢弃
parser中每个状态执行0次或以上后转换为其他状态(允许循环)
transition
关键字用于parser
在状态之间转换,例如transition accept;
transition select(data){...}
可根据data
的值转换到不同状态,类似于C语言中的switch case
,但不需要用break语句跳出
control部分
control类似于C语言中的函数(不能有循环):
- 在control中,可以声明变量、创建tables,以及实例化
externs
等 - 具体的功能由
apply{}
中的代码进行声明
action关键字:
- 类似于C语言中的函数
action
可以在control
内声明,也可以在control
外全局定义- action的参数有类型与方向(有in, out, inout)
关于table:
- 指定要匹配(match)的数据和匹配类型(有exact精确匹配、ternary、lpm最长前缀匹配等)
- 指定一系列可能的actions
- 可以选择性地指定一些table属性,包括size,default_action(默认动作),const enries
- 要在
apply{}
中添加table名.apply()
才能应用这个table - 每个table都有一或多个entries(rules),一个entry中包括:
- 用于匹配的特定key
- 当数据包匹配这个entry时,一个
action
将被执行 - action data(可能为空)
deparser部分
deparser
将headers按顺序组装到数据报中,使用control
功能进行表示即可
emit(hdr)
:如果该报头有效,则将其按序组装到数据报中