Transport table debug information to controller
This commit is contained in:
parent
e1146070c4
commit
9ca4d4c8de
4 changed files with 88 additions and 26 deletions
52
doc/plan.org
52
doc/plan.org
|
@ -422,7 +422,24 @@ Problem: task field might be overriden for controller use in different
|
|||
table -> need different task field!
|
||||
|
||||
***** try2: checksum ok, but no packets on h3
|
||||
****** Setup a default rule for the IPv4 world to debug on controller
|
||||
****** DONE Setup a default rule for the IPv4 world to debug on controller
|
||||
Still not seeing the converted packet, however seeing icmp6_ns packets
|
||||
which should not be there:
|
||||
|
||||
table entry for ns:
|
||||
|
||||
ff:02:00:00:00:00:00:00:00:00:00:01:ff:00:00:42/128
|
||||
|
||||
debug packet seen in controller:
|
||||
|
||||
DEBUG:main:v6 reassambled=<Ether dst=33:33:ff:00:00:42 src=00:00:0a:00:00:01 type=0x86dd |<IPv6 version=6 tc=0 fl=0 plen=32 nh=ICMPv6 hlim=255 src=fe80::200:aff:fe00:1 dst=ff02::1:ff00:42 |<ICMPv6ND_NS type=Neighbor Solicitation code=0 cksum=0x37df res=0 tgt=2001:db8::42 |<ICMPv6NDOptSrcLLAddr type=1 len=1 lladdr=00:00:0a:00:00:01 |>>>>
|
||||
DEBUG:main:v6 reassambled=<Ether dst=33:33:ff:00:00:42 src=00:00:0a:00:00:01 type=0x86dd |<IPv6 version=6 tc=0 fl=0 plen=32 nh=ICMPv6 hlim=255 src=fe80::200:aff:fe00:1 dst=ff02::1:ff00:42 |<ICMPv6ND_NS type=Neighbor Solicitation code=0 cksum=0x37df res=0 tgt=2001:db8::42 |<ICMPv6NDOptSrcLLAddr type=1 len=1 lladdr=00:00:0a:00:00:01 |>>>>
|
||||
DEBUG:main:v6 reassambled=<Ether dst=33:33:ff:00:00:42 src=00:00:0a:00:00:01 type=0x86dd |<IPv6 version=6 tc=0 fl=0 plen=32 nh=ICMPv6 hlim=255 src=2001:db8::1 dst=ff02::1:ff00:42 |<ICMPv6ND_NS type=Neighbor Solicitation code=0 cksum=0x13a7 res=0 tgt=2001:db8::42 |<ICMPv6NDOptSrcLLAddr type=1 len=1 lladdr=00:00:0a:00:00:01 |>>>>
|
||||
|
||||
DEBUG:main:v6 reassambled=<Ether dst=00:00:0a:00:00:42 src=00:00:0a:00:00:01 type=0x86dd |<IPv6 version=6 tc=0 fl=920946 plen=64 nh=ICMPv6 hlim=64 src=2001:db8::1 dst=2001:db8:1::a00:1 |<ICMPv6EchoRequest type=Echo Request code=0 cksum=0xf981 id=0x5f7c seq=0x1 data='N\xc6\x98\\\x00\x00\x00\x00\x12\x1b\t\x00\x00\x00\x00\x00\x10\x11\x12\x13\x14\x15\x16\x17\x18\x19\x1a\x1b\x1c\x1d\x1e\x1f !"#$%&\'()*+,-./01234567' |>>>
|
||||
|
||||
debugging MIGHT come from nat64 table!
|
||||
|
||||
|
||||
*** TODO Get p4 VM / vagrant running
|
||||
**** DONE install libvirtd-daemon
|
||||
|
@ -1219,8 +1236,8 @@ debug packets - analyse code - goto 1
|
|||
[21:26] line:~% sudo apt install thrift-compiler
|
||||
libnanomsg-dev libjudy-dev
|
||||
*** Performance comparison
|
||||
*** Feature/Functionality difference / overview / CHALLENGES / LIMITATIONS in P4
|
||||
**** P4: cannot read key from table
|
||||
*** Challenges / Limitations in P4
|
||||
**** DONE cannot read key from table
|
||||
***** log
|
||||
Key and mask for matching destination is in table. We need this
|
||||
information in the action. However this information is not exposed, so
|
||||
|
@ -1285,7 +1302,7 @@ Need to duplicate information
|
|||
**** DONE ICMP6: checksum over payload
|
||||
- variable length, up to 65k
|
||||
Exists!
|
||||
**** Synchronisation with the controller
|
||||
**** DONE Synchronisation with the controller
|
||||
- Double data type definition -> might differ
|
||||
- TYPE_CPU for ethernet
|
||||
- Port ingress offset (9 vs. 16 bit)
|
||||
|
@ -1315,18 +1332,29 @@ Code:
|
|||
}
|
||||
#+END_SRC
|
||||
|
||||
**** (current) Implementation limitations
|
||||
***** No fragmentation support (yet)
|
||||
***** No session handling (yet)
|
||||
**** No table meta information for default actions (asked 2019-03-25)
|
||||
Is there any meta information for "from which table was the action
|
||||
called" available? My use case is having a debug action that sends
|
||||
packets to the controller and I use it as a default_action in various
|
||||
tables; however know I don't know anymore from which table the action
|
||||
was called. Is there any kind of meta information which table called
|
||||
me available?
|
||||
|
||||
I could work around this by using if(! .. .hit) { my_action(table_id)
|
||||
}, but it would not work with using default_action = ...
|
||||
|
||||
*** Implementation limitations
|
||||
**** No fragmentation support (yet)
|
||||
**** No session handling (yet)
|
||||
1:1 mappings. No (automatic) session.
|
||||
***** IPv4 / IPv6 embedding
|
||||
**** IPv4 / IPv6 embedding
|
||||
Currently offset based - probably not following the RFC!
|
||||
***** No DNS64
|
||||
**** No DNS64
|
||||
has already been solved in a different domain - could even do
|
||||
transparent / in network modification
|
||||
***** Incomplete NDP
|
||||
Very limited option support
|
||||
***** NAT64 mappings not source network dependent
|
||||
**** Incomplete NDP
|
||||
Very limited option support
|
||||
**** NAT64 mappings not source network dependent
|
||||
Only the destination network is matched for deciding on NAT64, as
|
||||
priority based double LPM is not supported. This limits a prefix to be
|
||||
used only in one network.
|
||||
|
|
|
@ -23,11 +23,20 @@ log = logging.getLogger("main")
|
|||
|
||||
|
||||
cpu_fields = {
|
||||
0: 'UNSET',
|
||||
1: 'ICMP6_NS',
|
||||
2: 'ICMP6_GENERAL',
|
||||
3: 'DEBUG'
|
||||
}
|
||||
|
||||
table_id_fields = {
|
||||
0: 'UNSET_TABLE',
|
||||
1: 'TABLE_NAT64',
|
||||
2: 'TABLE_ICMP6,
|
||||
3: 'TABLE_V6_NETWORKS,
|
||||
4: 'TABLE_NAT46',
|
||||
5: 'TABLE_V4_NETWORKS'
|
||||
}
|
||||
|
||||
class CpuHeader(Packet):
|
||||
name = 'CpuPacket'
|
||||
|
@ -35,6 +44,7 @@ class CpuHeader(Packet):
|
|||
ShortEnumField('task', 1, cpu_fields ),
|
||||
ShortField('ingress_port', 0),
|
||||
XShortEnumField("type", 0x9000, ETHER_TYPES)
|
||||
ShortEnumField('table_id', 1, table_id_fields ),
|
||||
]
|
||||
|
||||
|
||||
|
@ -421,8 +431,6 @@ class L2Controller(object):
|
|||
def recv_msg_cpu(self, pkg):
|
||||
packet = Ether(str(pkg))
|
||||
|
||||
|
||||
|
||||
if packet.type == 0x0800:
|
||||
log.debug("Received raw (untagged) packet - BUG")
|
||||
self.debug_print_pkg(pkg)
|
||||
|
@ -432,13 +440,14 @@ class L2Controller(object):
|
|||
cpu_header = CpuHeader(packet.payload)
|
||||
ether_orig = Ether(src=packet.src, dst=packet.dst, type=cpu_header.type)
|
||||
orig_packet = ether_orig / IP(cpu_header.load)
|
||||
log.debug("cpu = {}".format(cpu_header.__repr__()))
|
||||
log.debug("v4 reassambled={}".format(orig_packet.__repr__()))
|
||||
|
||||
elif packet.type == 0x4242:
|
||||
cpu_header = CpuHeader(packet.payload)
|
||||
|
||||
# Not necessary anymore - cpu decoding works
|
||||
# log.debug("cpu = {}".format(cpu_header.__repr__()))
|
||||
log.debug("cpu = {}".format(cpu_header.__repr__()))
|
||||
|
||||
ether_orig = Ether(src=packet.src, dst=packet.dst, type=cpu_header.type)
|
||||
|
||||
|
@ -454,7 +463,7 @@ class L2Controller(object):
|
|||
src = orig_packet['IPv6'].src
|
||||
log.debug("Router solicitation from {} -- should probably handle this?".format(src))
|
||||
elif cpu_header.task == self.task['DEBUG']:
|
||||
log.debug("v6 reassambled={}".format(orig_packet.__repr__()))
|
||||
log.debug("[debug] v6 reassambled={}".format(orig_packet.__repr__()))
|
||||
elif cpu_header.task == self.task['ICMP6_NS']:
|
||||
log.info("Doing neighbor solicitation for the switch in the controller")
|
||||
self.handle_icmp6_ns(orig_packet)
|
||||
|
|
|
@ -12,6 +12,14 @@ typedef bit<9> port_t;
|
|||
typedef bit<16> mcast_t;
|
||||
typedef bit<16> task_t;
|
||||
|
||||
typedef bit<8> table_t; /* to map debug messages */
|
||||
|
||||
const bit<8> TABLE_NAT64 = 1;
|
||||
const bit<8> TABLE_ICMP6 = 2;
|
||||
const bit<8> TABLE_V6_NETWORKS = 3;
|
||||
const bit<8> TABLE_NAT46 = 4;
|
||||
const bit<8> TABLE_V4_NETWORKS = 5;
|
||||
|
||||
|
||||
const bit<16> TYPE_IPV4 = 0x0800;
|
||||
const bit<16> TYPE_IPV6 = 0x86DD;
|
||||
|
@ -148,6 +156,7 @@ header cpu_t {
|
|||
task_t task;
|
||||
bit<16> ingress_port;
|
||||
bit<16> ethertype;
|
||||
table_t table_id;
|
||||
}
|
||||
|
||||
struct headers {
|
||||
|
@ -169,6 +178,7 @@ struct metadata {
|
|||
task_t switch_task;
|
||||
bit<16> tcp_length;
|
||||
bit<32> cast_length;
|
||||
table_t table_id;
|
||||
}
|
||||
|
||||
#endif
|
|
@ -32,6 +32,11 @@ control MyIngress(inout headers hdr,
|
|||
clone3(CloneType.I2E, 100, meta);
|
||||
}
|
||||
|
||||
action controller_debug_table_id(table_t table_id) {
|
||||
hdr.cpu.table_id = table_id;
|
||||
controller_reply(TASK_DEBUG);
|
||||
}
|
||||
|
||||
action controller_debug() {
|
||||
controller_reply(TASK_DEBUG);
|
||||
}
|
||||
|
@ -242,7 +247,6 @@ control MyIngress(inout headers hdr,
|
|||
}
|
||||
size = NDP_TABLE_SIZE;
|
||||
default_action = NoAction;
|
||||
// default_action = controller_debug;
|
||||
}
|
||||
|
||||
/* Handle multicast registration of NDP */
|
||||
|
@ -257,7 +261,6 @@ control MyIngress(inout headers hdr,
|
|||
}
|
||||
size = NDP_TABLE_SIZE;
|
||||
default_action = NoAction;
|
||||
// default_action = controller_debug;
|
||||
}
|
||||
|
||||
/********************** NDP support for OTHERS (unused ATM) ***********************************/
|
||||
|
@ -273,7 +276,7 @@ control MyIngress(inout headers hdr,
|
|||
NoAction;
|
||||
}
|
||||
size = NDP_TABLE_SIZE;
|
||||
default_action = controller_debug;
|
||||
default_action = NoAction;
|
||||
}
|
||||
|
||||
|
||||
|
@ -306,7 +309,7 @@ control MyIngress(inout headers hdr,
|
|||
NoAction;
|
||||
}
|
||||
size = ROUTING_TABLE_SIZE;
|
||||
default_action = controller_debug;
|
||||
default_action = NoAction;
|
||||
}
|
||||
|
||||
table v4_networks {
|
||||
|
@ -319,19 +322,30 @@ control MyIngress(inout headers hdr,
|
|||
NoAction;
|
||||
}
|
||||
size = ROUTING_TABLE_SIZE;
|
||||
default_action = controller_debug;
|
||||
default_action = NoAction;
|
||||
}
|
||||
|
||||
/********************** APPLYING TABLES ***********************************/
|
||||
apply {
|
||||
if(hdr.ipv6.isValid()) {
|
||||
icmp6.apply(); /* icmp6 echo, icmp6 ndp */
|
||||
nat64.apply(); /* v6 -> v4 */
|
||||
v6_networks.apply(); /* routing, egress */
|
||||
if(!icmp6.apply().hit) { /* icmp6 echo, icmp6 ndp */
|
||||
controller_debug_table_id(TABLE_ICMP6);
|
||||
}
|
||||
|
||||
if(!nat64.apply().hit) { /* v6 -> v4 */
|
||||
controller_debug_table_id(TABLE_NAT64);
|
||||
}
|
||||
if(!v6_networks.apply().hit) {
|
||||
controller_debug_table_id(TABLE_V6_NETWORKS);
|
||||
}
|
||||
}
|
||||
if(hdr.ipv4.isValid()) {
|
||||
nat46.apply(); /* v4->v6 */
|
||||
v4_networks.apply(); /* routing, egress */
|
||||
if(!nat46.apply().hit) { /* v4->v6 */
|
||||
controller_debug_table_id(TABLE_NAT46);
|
||||
}
|
||||
if(!v4_networks.apply().hit) { /* routing, egress */
|
||||
controller_debug_table_id(TABLE_V4_NETWORKS)
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -351,6 +365,7 @@ control MyEgress(inout headers hdr,
|
|||
hdr.cpu.ethertype = hdr.ethernet.ethertype;
|
||||
hdr.cpu.ingress_port = (bit<16>) meta.ingress_port;
|
||||
|
||||
|
||||
hdr.ethernet.ethertype = TYPE_CPU;
|
||||
}
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue