博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
P4语言编程快速开始 实践一
阅读量:6788 次
发布时间:2019-06-26

本文共 20583 字,大约阅读时间需要 68 分钟。

参考: 感谢杨老师的分享!

前言及P4程序请参考原文,本文主要是对文章中的两个动手实例的实践记录。

1.通过behavioral-model运行simple_router样例

执行命令:

cd p4factory/targets/simple_routermake bmsudo ./behavioral-model

在本地启动一个behavior-model,默认使用PD RPC服务的地址为127.0.0.1:9090

当在同一台宿主机上启动多个bmv2时,可以使用--pd-server=IP:PORT指定不同的端口,以防止端口占用冲突。更多参数可以使用-h参数查看CLI帮助。

执行./behavioral-model之后显示如下:

Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]outgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 2 length 107; first bytes:33330000 00fffffffbfffffffaffffffcb ffffffaf6d3effffff8c ffffff86ffffffdd600bnew packet, len : 107, ingress : 2rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb924000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 0 length 107; first bytes:33330000 00fffffffb1213 ffffff91ffffffdefffffffe30 ffffff86ffffffdd6008new packet, len : 107, ingress : 0rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb928000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 6 length 107; first bytes:33330000 00fffffffbfffffffa51 fffffff66e382d ffffff86ffffffdd600enew packet, len : 107, ingress : 6rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb91c000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 1 length 107; first bytes:33330000 00fffffffb1effffffee 1943ffffffc0ffffffb8 ffffff86ffffffdd6003new packet, len : 107, ingress : 1rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb934000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 7 length 107; first bytes:33330000 00fffffffb3e7a ffffffb10bffffff97ffffffe8 ffffff86ffffffdd600anew packet, len : 107, ingress : 7rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb920000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 4 length 107; first bytes:33330000 00fffffffbffffff92ffffffe4 4a34ffffff9fffffffeb ffffff86ffffffdd600bnew packet, len : 107, ingress : 4rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb914000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 5 length 107; first bytes:33330000 00fffffffb2e33 672a7cffffffef ffffff86ffffffdd600fnew packet, len : 107, ingress : 5rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb918000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 0 length 107; first bytes:33330000 00fffffffb4a23 66ffffffe1724a ffffff86ffffffdd600dnew packet, len : 107, ingress : 0rmt proc returns 0Packet in on port 6 length 107; first bytes:33330000 00fffffffbffffffde59 680dffffffc046 ffffff86ffffffdd600enew packet, len : 107, ingress : 6rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb928000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]queuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb91c000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 2 length 107; first bytes:33330000 00fffffffbffffffd2ffffffd8 19ffffffce47ffffff99 ffffff86ffffffdd6009new packet, len : 107, ingress : 2rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb924000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 3 length 107; first bytes:33330000 00fffffffbfffffff6ffffffdb 21fffffffbffffffa97f ffffff86ffffffdd600dnew packet, len : 107, ingress : 3rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb930000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 4 length 107; first bytes:33330000 00fffffffbffffffdaffffffec ffffffd4ffffff8fffffffed33 ffffff86ffffffdd600anew packet, len : 107, ingress : 4rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb914000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]Packet in on port 5 length 107; first bytes:33330000 00fffffffb1221 447dffffffd3ffffff94 ffffff86ffffffdd6006new packet, len : 107, ingress : 5rmt proc returns 0ingress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93one checksum is incorrectApplying table ipv4_lpmLookup key for ipv4_lpm:    ipv4_dstAddr: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernettotal length for outgoing meta: 24copying metadatadeparsing standard_metadatadeparsing routing_metadataqueuing system: packet dequeuedegress port set to 0instance type set to 0egress_pipeline: packet dequeuedparsing startparsing parse_ethernetpayload length: 93extracting metadataextracting all metadata for 0x7fb918000940Applying table send_frameLookup key for send_frame:    standard_metadata_egress_port: 0x00000000, table miss, applying default actionno default action, doing nothingtotal length for outgoing pkt: 107deparsing ethernetoutgoing thread: packet dequeuedoutgoing thread: sending pkt: Size[107]: Port[0]In client_init

之后运行./run_cli.bash脚本,访问simple_router的运行时API:

root@FZUSDNLab:/home/sdn/p4factory/targets/simple_router# ./run_cli.bash Using default thrift server and port localhost:9090(Cmd) ?Documented commands (type help 
):========================================EOF dump_table mc_node_destroy add_entry exit mc_node_update add_entry_with_member get_first_entry_handle modify_entry add_entry_with_selector get_next_entry_handles quit add_member help set_default_actionadd_member_to_group mc_associate_node show_actions create_group mc_dissociate_node show_entry delete_entry mc_mgrp_create show_tables delete_group mc_mgrp_destroy delete_member mc_node_create (Cmd)

2.通过run_demo.bash脚本 运行启动simple_router示例

注:如果之前进行了第一步,请重启再重新开启虚拟端口,方法是进入p4factory/tools目录下,执行:

./veth_setup.sh

进入simple_router目录,执行run_demo.bash脚本使用mininet构建网络拓扑:

./run_demo.bash

执行后效果如下:

root@FZUSDNLab:/home/sdn/p4factory/targets/simple_router# ./run_demo.bash *** Creating network*** Adding hosts:h1 h2 *** Adding switches:s1 *** Adding links:(h1, s1) (h2, s1) *** Configuring hostsh1 h2 *** Starting controller*** Starting 1 switchess1 Starting P4 switch s1/home/sdn/p4factory/targets/simple_router/behavioral-model --name s1 --dpid 0000000000000001 -i s1-eth1 -i s1-eth2 --listener 127.0.0.1:11111 --pd-server 127.0.0.1:22222 switch has been started**********h1default interface: eth0 10.0.0.10   00:04:00:00:00:00********************h2default interface: eth0 10.0.1.10   00:04:00:00:00:01**********Ready !*** Starting CLI:mininet>

注意,此时PD服务端口不再是9090,直接运行run_cli.bash脚本无法访问simple_router的运行时CLI。

有两种方法解决这个问题,一种是修改bash脚本,这里请参照原文。

另外一种是直接采用-c参数指定端口号,笔者采用的是这种方法:

./run_cli.bash -c 127.0.0.1:22222

效果如下:

root@ubuntu:/home/wasdns/p4factory/targets/simple_router# ./run_cli.bash -c 127.0.0.1:22222(Cmd)

查看此时P4交换机中的流表:

(Cmd) show_tablesforwardipv4_lpmsend_frame(Cmd) dump_table forwardNo entry handle found(Cmd) dump_table ipv4_lpmNo entry handle found(Cmd) dump_table send_frameNo entry handle found(Cmd)

此时P4交换机中有三张流表,但是都没有内容。

证明了在只有数据平面的情况下,不同host之间是没有办法正常通信的。此时也有两种方法充当控制平面。

(1)通过运行run_add_demo_entries.bash脚本下发流表。其内容如下:

python ../../cli/pd_cli.py -p simple_router -i p4_pd_rpc.simple_router -s $PWD/tests/pd_thrift:$PWD/../../testutils -m "add_entry send_frame 1 rewrite_mac 00:aa:bb:00:00:00" -c localhost:22222python ../../cli/pd_cli.py -p simple_router -i p4_pd_rpc.simple_router -s $PWD/tests/pd_thrift:$PWD/../../testutils -m "add_entry send_frame 2 rewrite_mac 00:aa:bb:00:00:01" -c localhost:22222python ../../cli/pd_cli.py -p simple_router -i p4_pd_rpc.simple_router -s $PWD/tests/pd_thrift:$PWD/../../testutils -m "add_entry forward 10.0.0.10 set_dmac 00:04:00:00:00:00" -c localhost:22222python ../../cli/pd_cli.py -p simple_router -i p4_pd_rpc.simple_router -s $PWD/tests/pd_thrift:$PWD/../../testutils -m "add_entry forward 10.0.1.10 set_dmac 00:04:00:00:00:01" -c localhost:22222python ../../cli/pd_cli.py -p simple_router -i p4_pd_rpc.simple_router -s $PWD/tests/pd_thrift:$PWD/../../testutils -m "add_entry ipv4_lpm 10.0.0.10 32 set_nhop 10.0.0.10 1" -c localhost:22222python ../../cli/pd_cli.py -p simple_router -i p4_pd_rpc.simple_router -s $PWD/tests/pd_thrift:$PWD/../../testutils -m "add_entry ipv4_lpm 10.0.1.10 32 set_nhop 10.0.1.10 2" -c localhost:22222

执行./run_add_demo_entries.bash为P4交换机增添表项。

执行之后如下:

Inserted entry with handle 0Inserted entry with handle 1Inserted entry with handle 0Inserted entry with handle 1Inserted entry with handle 0Inserted entry with handle 1

在CLI中查看流表:

1.forward:

(Cmd) dump_table forwardEntry handle 0    key:        routing_metadata_nhop_ipv4: 0x0a00000a (10 0 0 10),     action:        set_dmac    action data:        dmac: 0x000400000000,   Entry handle 1    key:        routing_metadata_nhop_ipv4: 0x0a00010a (10 0 1 10),     action:        set_dmac    action data:        dmac: 0x000400000001,   (Cmd)

2.ipv4_lpm

(Cmd) dump_table ipv4_lpmEntry handle 0    key:        ipv4_dstAddr: 0x0a00000a (10 0 0 10),       prefix_length:        32    action:        set_nhop    action data:        nhop_ipv4: 0x0a00000a (10 0 0 10),  port: 0x00000001 (0 0 0 1), Entry handle 1    key:        ipv4_dstAddr: 0x0a00010a (10 0 1 10),       prefix_length:        32    action:        set_nhop    action data:        nhop_ipv4: 0x0a00010a (10 0 1 10),  port: 0x00000002 (0 0 0 2), (Cmd)

3.send_frame

(Cmd) dump_table send_frameEntry handle 0    key:        standard_metadata_egress_port: 0x00000001 (0 0 0 1),        action:        rewrite_mac    action data:        smac: 0x00aabb000000,   Entry handle 1    key:        standard_metadata_egress_port: 0x00000002 (0 0 0 2),        action:        rewrite_mac    action data:        smac: 0x00aabb000001,   (Cmd)

在mininet中能够ping通:

885822-20170115233337853-489099479.png

(2)编写command.txt,并通过behavioral-model/tools/runtimeCLI下发流表。

在运行之前,请先安装bmv2(behavioral-model),可以参考我的另外一篇博客:

command.txt内容如下:

table_set_default send_frame _droptable_set_default forward _droptable_set_default ipv4_lpm _droptable_add send_frame rewrite_mac 1 => 00:aa:bb:00:00:00table_add send_frame rewrite_mac 2 => 00:aa:bb:00:00:01table_add forward set_dmac 10.0.0.10 => 00:04:00:00:00:00table_add forward set_dmac 10.0.1.10 => 00:04:00:00:00:01table_add ipv4_lpm set_nhop 10.0.0.10/32 => 10.0.0.10 1table_add ipv4_lpm set_nhop 10.0.1.10/32 => 10.0.1.10 2

原文中命令有误,是无法执行的,这里先暂时使用第一种方法,后续会补充上。

从这些流表下发方法中也可以认识到以下几点:

a)没有控制面下发的流表,仅数据面无法工作。
b)控制面下发的流表必须与P4程序中定义的table相吻合,从匹配字段(match-field)到动作(action).
c)P4定义的数据面所对应的控制面,可以是控制器、运行时CLI,也可以是SAI等。

2017/1/15

转载地址:http://bbsgo.baihongyu.com/

你可能感兴趣的文章
【转】着色中的数学和物理原理
查看>>
Position Independent Code (PIC) in shared libraries on x64
查看>>
接口继承和实现继承的区别
查看>>
spring 的自建request请求
查看>>
数组的相关知识
查看>>
Python中的logger和handler到底是个什么鬼
查看>>
mysql之 openark-kit online ddl
查看>>
mydumper安装、原理介绍
查看>>
值类型和引用类型的详细讨论
查看>>
入门Webpack,看这篇就够了
查看>>
Springboot中关于跨域问题的一种解决方法
查看>>
PHP和Apache的安装
查看>>
要让div中的float不会自动显示到下一行来?
查看>>
五种排序方法(选择、冒泡、快排、插入、希尔)
查看>>
位运算及其应用实例(1)
查看>>
vim相关
查看>>
捐助账号
查看>>
线程交替运行
查看>>
ubuntu10.04 –像QQ一样截屏,注解
查看>>
三年观察揭示TNF抑制剂持续改善强柱患者躯体功能的预测因子
查看>>