【p4tutorials】P4 v1.1 Simple Router
fork了p4tutorials,想从里面窥探一些门道。
本文相关的原文链接:ReadMe
说明:
下面的这个P4程序,是当下最著名的 simple_router 程序的一个版本,是根据P4的1.1版本描述的。
除了这个程序之外,这个版本的p4可以根据失效的TTL字段跟踪Drop的IPv4报文;这个程序是用来说明P41.1版本的一些潜在功能,具体请移步P4.org。
Look at the P4 program and observe some of the P4 v1.1 additions:
- strong typing in header type definitions and action declarations
- assignment with = instead of modify_field (extension to the v1.1 spec)
- register indexing
- support for the ternary operator (extension to the v1.1 spec)
跑这个demo
他们提供了一个小的demo来帮助你测试这个程序,在跑这个程序之前,请确保env.sh这个文件(在这篇ReadMe的上层目录)是处在最新状态的。
To run the demo:
- start the switch in Mininet with
./run_switch.sh - in another terminal, populate the table entries with
./add_entries.sh - you should now be able to ping h2 from h1 by typing
h1 ping h2in the Mininet CLI
Once you have the basic demo running, you can start sending packets with a TTL of 1, activate packet drop tracking in the switch and observe the count go up. To do this:
- activate the tracking with
./register_on_off.shon - send ICMP packets with a TTL of 1 from the Mininet CLI:
h1 ping h2 -t 1. The packets are now dropped by the switch, so you should not be able to observe a reply
To get the drop count, simply run
./read_register.sh.
P4程序 位于 ../tutorials/p4v1_1/simple_router/p4src 目录下
/* Copyright 2013-present Barefoot Networks, Inc.
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
header_type ethernet_t {
fields {
bit<48> dstAddr;
bit<48> srcAddr;
bit<16> etherType;
}
}
header_type ipv4_t {
fields {
bit<4> version;
bit<4> ihl;
bit<8> diffserv;
bit<16> totalLen;
bit<16> identification;
bit<3> flags;
bit<13> fragOffset;
bit<8> ttl;
bit<8> protocol;
bit<16> hdrChecksum;
bit<32> srcAddr;
bit<32> dstAddr;
}
}
parser start {
return parse_ethernet;
}
#define ETHERTYPE_IPV4 0x0800
header ethernet_t ethernet;
parser parse_ethernet {
extract(ethernet);
return select(latest.etherType) {
ETHERTYPE_IPV4 : parse_ipv4;
default: ingress;
}
}
header ipv4_t ipv4;
field_list ipv4_checksum_list {
ipv4.version;
ipv4.ihl;
ipv4.diffserv;
ipv4.totalLen;
ipv4.identification;
ipv4.flags;
ipv4.fragOffset;
ipv4.ttl;
ipv4.protocol;
ipv4.srcAddr;
ipv4.dstAddr;
}
field_list_calculation ipv4_checksum {
input {
ipv4_checksum_list;
}
algorithm : csum16;
output_width : 16;
}
calculated_field ipv4.hdrChecksum {
verify ipv4_checksum;
update ipv4_checksum;
}
parser parse_ipv4 {
extract(ipv4);
return ingress;
}
action _drop() {
drop();
}
header_type routing_metadata_t {
fields {
bit<32> nhop_ipv4;
}
}
metadata routing_metadata_t routing_metadata;
register drops_register {
width: 32;
static: drop_expired;
instance_count: 16;
}
register drops_register_enabled {
width: 1;
static: drop_expired;
instance_count: 16;
}
action do_drop_expired() {
drops_register[0] = drops_register[0] + ((drops_register_enabled[0] == 1) ? (bit<32>)1 : 0);
drop();
}
table drop_expired {
actions { do_drop_expired; }
size: 0;
}
action set_nhop(in bit<32> nhop_ipv4, in bit<9> port) {
routing_metadata.nhop_ipv4 = nhop_ipv4;
standard_metadata.egress_spec = port;
ipv4.ttl = ipv4.ttl - 1;
}
table ipv4_lpm {
reads {
ipv4.dstAddr : lpm;
}
actions {
set_nhop;
_drop;
}
size: 1024;
}
action set_dmac(in bit<48> dmac) {
ethernet.dstAddr = dmac;
// modify_field still valid
// modify_field(ethernet.dstAddr, dmac);
}
table forward {
reads {
routing_metadata.nhop_ipv4 : exact;
}
actions {
set_dmac;
_drop;
}
size: 512;
}
action rewrite_mac(in bit<48> smac) {
ethernet.srcAddr = smac;
}
table send_frame {
reads {
standard_metadata.egress_port: exact;
}
actions {
rewrite_mac;
_drop;
}
size: 256;
}
control ingress {
if(valid(ipv4)) {
if(ipv4.ttl > 1) {
apply(ipv4_lpm);
apply(forward);
} else {
apply(drop_expired);
}
}
}
control egress {
apply(send_frame);
}
【p4tutorials】P4 v1.1 Simple Router的更多相关文章
- 【设计模式】简单工厂模式 Simple Factory Pattern
简单工厂模式Simple Factory Pattern[Simple Factory Pattern]是设计模式里最简单的一个模式,又叫静态工厂模式[Static Factory Pattern], ...
- 【翻译】Kinect v1和Kinect v2的彻底比较
本连载主要是比较Kinect for Windows的现行版(v1)和次世代型的开发者预览版(v2),以C++开发者为背景介绍进化的硬件和软件.本文主要是对传感的配置和运行条件进行彻底的比较. ...
- 【php】下载站系统Simple Down v5.5.1 xss跨站漏洞分析
author:zzzhhh 一. 跨站漏洞 利用方法1,直接在搜索框处搜索<script>alert(/xss/)</script>//',再次刷新,跨站语句将被 ...
- 【代码审计】BootCMS v1.1.3 文件上传漏洞分析
0x00 环境准备 BootCMS官网:http://www.kilofox.net 网站源码版本:BootCMS v1.1.3 发布日期:2016年10月17日 程序源码下载:http://w ...
- 【数论】HDU 4143 A Simple Problem
题目内容 给出一个正整数\(n\),找到最小的正整数\(x\),使之能找到一个整数\(y\),满足\(y^2=n+x^2\). 输入格式 第一行是数据组数\(T\),每组数据有一个整数\(n\). 输 ...
- 数据结构【一】:简单队列simple queue
简单的FIFO队列实现,非线程安全! 1.queue.h : abstract data type queue #ifndef CUR_QUEUE_H #define CUR_QUEUE_H #inc ...
- 【HDOJ】1088 Write a simple HTML Browser
题目其实不难,但是要注意题目的要求,当前字数(>0)+当前单词长度+1若超过80则需要回车后,输出当前word,并且重新计数.这道题目的数据感觉比较水,不过测试的时候,最后使用fprintf输出 ...
- 【35】单层卷积网络(simple convolution)
今天我们要讲的是如何构建卷积神经网络的卷积层,下面来看个例子. 上节课,我们已经讲了如何通过两个过滤器卷积处理一个三维图像,并输出两个不同的4×4矩阵.假设使用第一个过滤器进行卷积,得到第一个4× ...
- 【Vulnhub】FristiLeaks v1.3
靶机信息 下载连接 https://download.vulnhub.com/fristileaks/FristiLeaks_1.3.ova.torrent https://download.vuln ...
随机推荐
- 正则表达式—RegEx(RegularExpressio)(三)
今日随笔,继续写一点关于正则表达式的 知识.前两天介绍了正则表达式验证匹配,提取等一些基本的知识,今天继续分享下它的另一个强大的应用:替换(replace). 开始之前,还是要补一下昨天的内容. 在我 ...
- MySQL Server has gone away报错原因汇总分析(转自:http://cenalulu.github.io/mysql/mysql-has-gone-away/)
原因1. MySQL 服务宕了 判断是否属于这个原因的方法很简单,执行以下命令,查看mysql的运行时长 $ mysql -uroot -p -e "show global status l ...
- 模拟退火算法(run away poj1379)
http://poj.org/problem?id=1379 Run Away Time Limit: 3000MS Memory Limit: 65536K Total Submissions: ...
- linix防火墙设置之顺序设置问题 -- 解决防火墙规则顺序和插入规则到指定序号的问题
转载于百度经验:https://jingyan.baidu.com/article/ae97a646ce58c2bbfd461d90.html 无论是硬件防火墙还是软件防火墙都会有一个规则序列的问题, ...
- javascript飞机大战-----005创建子弹对象2
子弹销毁 /* 创建子弹:因为子弹不是只创建一个所以要用构造函数 注意一点:子弹发射的位置应该是英雄机的正中央的位置,所以需要传点东西进来 */ function Bullet(l,t){ this. ...
- 关于Python装饰器内层函数为什么要return目标函数的一些个人见解
https://blog.csdn.net/try_test_python/article/details/80802199 前几天在学装饰器的时候,关于装饰器内层函数调用目标函数时是否return目 ...
- 20144306《网络对抗》MAL_后门原理与实践
本期收获 1.了解后门的基本概念. 2.Netcat.socat.MSF meterpreter的使用(MSF meterpreter实在太好玩了) 3.后门软件的启动方式: Windows任务计划程 ...
- Android仿今日头条手界面
public class MyIndicator extends HorizontalScrollView implements ViewPager.OnPageChangeListener { pr ...
- [World Wind学习]22.相机高度和瓦片等级计算
在这里我们看到判断Lod的级别主要有三个条件: * 1.相机视角范围,视角范围越大,所包含的tileSize就越大 * 2.相机与瓦片距离,距离越远,所包含的tileSize也就越大 * 3.相机视锥 ...
- google浏览器插件安装
1:安装本地插件,直接将下载好的crx插件拖入到 chrome://extensions/ 的空白处 http://www.cnplugins.com/tool/outline-instal ...