Enhance os-ken to support Nicira PacketIn2

neutron ovs agent has to handle advanced packet_in
with custom userdata which is necessary to openflow-based
floating IP implementation, but current os-ken doesn't
have such infrastructure.

This story is to enhance os-ken in order that neutron ovs
agent can act as an advanced SDN controller to handle
advanced packet_in.

Story: #2008964
Task: #42600
Related-Bug: #1931953

Signed-off-by: Yi Yang <yangyi01@inspur.com>

Change-Id: I4f993be5dd4a5f48396c4be152da5b61ea92392f
This commit is contained in:
Yi Yang 2021-06-11 04:10:59 -04:00
parent 5312d23b43
commit bf25f07861
7 changed files with 565 additions and 0 deletions

View File

@ -143,6 +143,18 @@ NXT_PACKET_IN = 17
NXT_FLOW_AGE = 18
NXT_SET_ASYNC_CONFIG = 19
NXT_SET_CONTROLLER_ID = 20
NXT_PACKET_IN2 = 30
# nx_packet_in2_prop_type
NXPINT_PACKET = 0
NXPINT_FULL_LEN = 1
NXPINT_BUFFER_ID = 2
NXPINT_TABLE_ID = 3
NXPINT_COOKIE = 4
NXPINT_REASON = 5
NXPINT_METADATA = 6
NXPINT_USERDATA = 7
NXPINT_CONTINUATION = 8
# enum nx_role
NX_ROLE_OTHER = 0

View File

@ -1229,6 +1229,15 @@ oxm_types = [
# EXT-233 Output match Extension
# NOTE(yamamoto): The spec says uint64_t but I assume it's an error.
oxm_fields.ONFExperimenter('actset_output', 43, type_desc.Int4),
# Support for matching/setting xreg0-7
oxm_fields.PacketRegs('xreg0', 0, type_desc.Int8),
oxm_fields.PacketRegs('xreg1', 1, type_desc.Int8),
oxm_fields.PacketRegs('xreg2', 2, type_desc.Int8),
oxm_fields.PacketRegs('xreg3', 3, type_desc.Int8),
oxm_fields.PacketRegs('xreg4', 4, type_desc.Int8),
oxm_fields.PacketRegs('xreg5', 5, type_desc.Int8),
oxm_fields.PacketRegs('xreg6', 6, type_desc.Int8),
oxm_fields.PacketRegs('xreg7', 7, type_desc.Int8),
] + nicira_ext.oxm_types
oxm_fields.generate(__name__)

View File

@ -53,6 +53,7 @@ from os_ken import exception
from os_ken import utils
from os_ken.ofproto.ofproto_parser import StringifyMixin, MsgBase
from os_ken.ofproto import ether
from os_ken.ofproto import nicira_ext
from os_ken.ofproto import nx_actions
from os_ken.ofproto import ofproto_parser
from os_ken.ofproto import ofproto_common
@ -6492,6 +6493,169 @@ class ONFBundleAddMsg(OFPExperimenter):
self.buf += tail_buf
@_register_exp_type(ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_SET_PACKET_IN_FORMAT)
class NXTSetPacketInFormatMsg(OFPExperimenter):
def __init__(self, datapath, packet_in_format):
super(NXTSetPacketInFormatMsg, self).__init__(
datapath, ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_SET_PACKET_IN_FORMAT)
self.packet_in_format = packet_in_format
def _serialize_body(self):
msg_pack_into(ofproto.OFP_EXPERIMENTER_HEADER_PACK_STR,
self.buf, ofproto.OFP_HEADER_SIZE,
self.experimenter, self.exp_type)
msg_pack_into(nicira_ext.NX_SET_PACKET_IN_FORMAT_PACK_STR,
self.buf, ofproto.OFP_EXPERIMENTER_HEADER_SIZE,
self.packet_in_format)
@classmethod
def parser_subtype(cls, super_msg):
packet_in_format = struct.unpack_from(
nicira_ext.NX_SET_PACKET_IN_FORMAT_PACK_STR, super_msg.data)[0]
msg = cls(super_msg.datapath, packet_in_format)
msg.properties = []
return msg
@_register_exp_type(ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_PACKET_IN2)
class NXTPacketIn2(OFPExperimenter):
def __init__(self, datapath, properties=None):
super(NXTPacketIn2, self).__init__(
datapath, ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_PACKET_IN2)
self.properties = properties or []
self.data = None
self.total_len = None
self.buffer_id = None
self.table_id = None
self.cookie = None
self.reason = None
self.metadata = None
self.userdata = None
self.continuation = None
def _serialize_body(self):
bin_props = bytearray()
for p in self.properties:
bin_props += p.serialize()
msg_pack_into(ofproto.OFP_EXPERIMENTER_HEADER_PACK_STR,
self.buf, ofproto.OFP_HEADER_SIZE,
self.experimenter, self.exp_type)
self.buf += bin_props
@classmethod
def parser_subtype(cls, super_msg):
msg = cls(super_msg.datapath)
rest = super_msg.data
while rest:
p, rest = NXTPacketIn2Prop.parse(rest)
msg.properties.append(p)
msg._parse_property(p)
return msg
def _parse_property(self, p):
if p.type == nicira_ext.NXPINT_PACKET:
self.data = p.data
# Note: here total_len is length of packet but not msg
self.total_len = p.length
elif p.type == nicira_ext.NXPINT_FULL_LEN:
self.total_len = struct.unpack_from('!I', p.data)[0]
elif p.type == nicira_ext.NXPINT_BUFFER_ID:
self.buffer_id = struct.unpack_from('!I', p.data)[0]
elif p.type == nicira_ext.NXPINT_TABLE_ID:
self.table_id = struct.unpack_from('B', p.data)[0]
elif p.type == nicira_ext.NXPINT_COOKIE:
self.cookie = struct.unpack_from('!Q', p.data)[0]
elif p.type == nicira_ext.NXPINT_REASON:
self.reason = struct.unpack_from('!B', p.data)[0]
elif p.type == nicira_ext.NXPINT_METADATA:
self.metadata = p.data
elif p.type == nicira_ext.NXPINT_USERDATA:
self.userdata = p.data
elif p.type == nicira_ext.NXPINT_CONTINUATION:
self.continuation = p.data
class NXTPacketIn2Prop(OFPPropBase):
_TYPES = {}
_PROP_TYPE = None
def __init__(self, type_=None, length=None, data=None):
super(NXTPacketIn2Prop, self).__init__(type_, length)
self.data = data
@classmethod
def parse(cls, buf):
(type_, length) = struct.unpack_from(cls._PACK_STR, buf, 0)
rest = buf[utils.round_up(length, 8):]
try:
subcls = cls._TYPES[type_]
except KeyError:
subcls = OFPPropUnknown
prop = subcls.sub_parser(buf, type, length)
prop.type = type_
prop.length = length
return prop, rest
def serialize_body(self):
return self.data
@classmethod
def sub_parser(cls, buf, type, length):
p = cls(type, length - 4, buf[4:length])
return p
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_PACKET)
class NXTPacketIn2PropPacket(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_PACKET
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_FULL_LEN)
class NXTPacketIn2PropFullLen(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_FULL_LEN
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_BUFFER_ID)
class NXTPacketIn2PropBufferId(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_BUFFER_ID
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_TABLE_ID)
class NXTPacketIn2PropTableId(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_TABLE_ID
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_COOKIE)
class NXTPacketIn2PropCookie(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_COOKIE
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_REASON)
class NXTPacketIn2PropReason(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_REASON
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_METADATA)
class NXTPacketIn2PropMetadata(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_METADATA
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_USERDATA)
class NXTPacketIn2PropUserData(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_USERDATA
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_CONTINUATION)
class NXTPacketIn2PropContinuation(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_CONTINUATION
nx_actions.generate(
'os_ken.ofproto.ofproto_v1_3',
'os_ken.ofproto.ofproto_v1_3_parser'

View File

@ -397,6 +397,15 @@ oxm_types = [
# EXT-233 Output match Extension
# NOTE(yamamoto): The spec says uint64_t but I assume it's an error.
oxm_fields.ONFExperimenter('actset_output', 43, type_desc.Int4),
# Support for matching/setting xreg0-7
oxm_fields.PacketRegs('xreg0', 0, type_desc.Int8),
oxm_fields.PacketRegs('xreg1', 1, type_desc.Int8),
oxm_fields.PacketRegs('xreg2', 2, type_desc.Int8),
oxm_fields.PacketRegs('xreg3', 3, type_desc.Int8),
oxm_fields.PacketRegs('xreg4', 4, type_desc.Int8),
oxm_fields.PacketRegs('xreg5', 5, type_desc.Int8),
oxm_fields.PacketRegs('xreg6', 6, type_desc.Int8),
oxm_fields.PacketRegs('xreg7', 7, type_desc.Int8),
] + nicira_ext.oxm_types
oxm_fields.generate(__name__)

View File

@ -29,6 +29,7 @@ from os_ken.lib.packet import packet
from os_ken import utils
from os_ken.ofproto.ofproto_parser import StringifyMixin, MsgBase, MsgInMsgBase
from os_ken.ofproto import ether
from os_ken.ofproto import nicira_ext
from os_ken.ofproto import nx_actions
from os_ken.ofproto import ofproto_parser
from os_ken.ofproto import ofproto_common
@ -52,6 +53,15 @@ def _register_parser(cls):
return cls
def _register_exp_type(experimenter, exp_type):
assert exp_type not in OFPExperimenter._subtypes
def _wrapper(cls):
OFPExperimenter._subtypes[(experimenter, exp_type)] = cls
return cls
return _wrapper
@ofproto_parser.register_msg_parser(ofproto.OFP_VERSION)
def msg_parser(datapath, version, msg_type, msg_len, xid, buf):
parser = _MSG_PARSERS.get(msg_type)
@ -407,6 +417,7 @@ class OFPExperimenter(MsgBase):
data Experimenter defined arbitrary additional data
============= =========================================================
"""
_subtypes = {}
def __init__(self, datapath, experimenter=None, exp_type=None, data=None):
super(OFPExperimenter, self).__init__(datapath)
@ -423,6 +434,13 @@ class OFPExperimenter(MsgBase):
ofproto.OFP_EXPERIMENTER_HEADER_PACK_STR, msg.buf,
ofproto.OFP_HEADER_SIZE)
msg.data = msg.buf[ofproto.OFP_EXPERIMENTER_HEADER_SIZE:]
if (msg.experimenter, msg.exp_type) in cls._subtypes:
new_msg = cls._subtypes[
(msg.experimenter, msg.exp_type)].parser_subtype(msg)
new_msg.set_headers(msg.version, msg.msg_type, msg.msg_len,
msg.xid)
new_msg.set_buf(msg.buf)
return new_msg
return msg
@ -5833,6 +5851,169 @@ class OFPBundleAddMsg(MsgInMsgBase):
self.buf += tail_buf
@_register_exp_type(ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_SET_PACKET_IN_FORMAT)
class NXTSetPacketInFormatMsg(OFPExperimenter):
def __init__(self, datapath, packet_in_format):
super(NXTSetPacketInFormatMsg, self).__init__(
datapath, ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_SET_PACKET_IN_FORMAT)
self.packet_in_format = packet_in_format
def _serialize_body(self):
msg_pack_into(ofproto.OFP_EXPERIMENTER_HEADER_PACK_STR,
self.buf, ofproto.OFP_HEADER_SIZE,
self.experimenter, self.exp_type)
msg_pack_into(nicira_ext.NX_SET_PACKET_IN_FORMAT_PACK_STR,
self.buf, ofproto.OFP_EXPERIMENTER_HEADER_SIZE,
self.packet_in_format)
@classmethod
def parser_subtype(cls, super_msg):
packet_in_format = struct.unpack_from(
nicira_ext.NX_SET_PACKET_IN_FORMAT_PACK_STR, super_msg.data)[0]
msg = cls(super_msg.datapath, packet_in_format)
msg.properties = []
return msg
@_register_exp_type(ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_PACKET_IN2)
class NXTPacketIn2(OFPExperimenter):
def __init__(self, datapath, properties=None):
super(NXTPacketIn2, self).__init__(
datapath, ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_PACKET_IN2)
self.properties = properties or []
self.data = None
self.total_len = None
self.buffer_id = None
self.table_id = None
self.cookie = None
self.reason = None
self.metadata = None
self.userdata = None
self.continuation = None
def _serialize_body(self):
bin_props = bytearray()
for p in self.properties:
bin_props += p.serialize()
msg_pack_into(ofproto.OFP_EXPERIMENTER_HEADER_PACK_STR,
self.buf, ofproto.OFP_HEADER_SIZE,
self.experimenter, self.exp_type)
self.buf += bin_props
@classmethod
def parser_subtype(cls, super_msg):
msg = cls(super_msg.datapath)
rest = super_msg.data
while rest:
p, rest = NXTPacketIn2Prop.parse(rest)
msg.properties.append(p)
msg._parse_property(p)
return msg
def _parse_property(self, p):
if p.type == nicira_ext.NXPINT_PACKET:
self.data = p.data
# Note: here total_len is length of packet but not msg
self.total_len = p.length
elif p.type == nicira_ext.NXPINT_FULL_LEN:
self.total_len = struct.unpack_from('!I', p.data)[0]
elif p.type == nicira_ext.NXPINT_BUFFER_ID:
self.buffer_id = struct.unpack_from('!I', p.data)[0]
elif p.type == nicira_ext.NXPINT_TABLE_ID:
self.table_id = struct.unpack_from('B', p.data)[0]
elif p.type == nicira_ext.NXPINT_COOKIE:
self.cookie = struct.unpack_from('!Q', p.data)[0]
elif p.type == nicira_ext.NXPINT_REASON:
self.reason = struct.unpack_from('!B', p.data)[0]
elif p.type == nicira_ext.NXPINT_METADATA:
self.metadata = p.data
elif p.type == nicira_ext.NXPINT_USERDATA:
self.userdata = p.data
elif p.type == nicira_ext.NXPINT_CONTINUATION:
self.continuation = p.data
class NXTPacketIn2Prop(OFPPropBase):
_TYPES = {}
_PROP_TYPE = None
def __init__(self, type_=None, length=None, data=None):
super(NXTPacketIn2Prop, self).__init__(type_, length)
self.data = data
@classmethod
def parse(cls, buf):
(type_, length) = struct.unpack_from(cls._PACK_STR, buf, 0)
rest = buf[utils.round_up(length, 8):]
try:
subcls = cls._TYPES[type_]
except KeyError:
subcls = OFPPropUnknown
prop = subcls.sub_parser(buf, type, length)
prop.type = type_
prop.length = length
return prop, rest
def serialize_body(self):
return self.data
@classmethod
def sub_parser(cls, buf, type, length):
p = cls(type, length - 4, buf[4:length])
return p
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_PACKET)
class NXTPacketIn2PropPacket(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_PACKET
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_FULL_LEN)
class NXTPacketIn2PropFullLen(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_FULL_LEN
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_BUFFER_ID)
class NXTPacketIn2PropBufferId(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_BUFFER_ID
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_TABLE_ID)
class NXTPacketIn2PropTableId(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_TABLE_ID
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_COOKIE)
class NXTPacketIn2PropCookie(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_COOKIE
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_REASON)
class NXTPacketIn2PropReason(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_REASON
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_METADATA)
class NXTPacketIn2PropMetadata(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_METADATA
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_USERDATA)
class NXTPacketIn2PropUserData(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_USERDATA
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_CONTINUATION)
class NXTPacketIn2PropContinuation(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_CONTINUATION
nx_actions.generate(
'os_ken.ofproto.ofproto_v1_4',
'os_ken.ofproto.ofproto_v1_4_parser'

View File

@ -432,6 +432,15 @@ oxm_types = [
oxm_fields.OpenFlowBasic('tcp_flags', 42, type_desc.Int2),
oxm_fields.OpenFlowBasic('actset_output', 43, type_desc.Int4),
oxm_fields.OpenFlowBasic('packet_type', 44, type_desc.Int4),
# Support for matching/setting xreg0-7
oxm_fields.PacketRegs('xreg0', 0, type_desc.Int8),
oxm_fields.PacketRegs('xreg1', 1, type_desc.Int8),
oxm_fields.PacketRegs('xreg2', 2, type_desc.Int8),
oxm_fields.PacketRegs('xreg3', 3, type_desc.Int8),
oxm_fields.PacketRegs('xreg4', 4, type_desc.Int8),
oxm_fields.PacketRegs('xreg5', 5, type_desc.Int8),
oxm_fields.PacketRegs('xreg6', 6, type_desc.Int8),
oxm_fields.PacketRegs('xreg7', 7, type_desc.Int8),
] + nicira_ext.oxm_types
oxm_fields.generate(__name__)

View File

@ -30,6 +30,7 @@ from os_ken import exception
from os_ken import utils
from os_ken.ofproto.ofproto_parser import StringifyMixin, MsgBase, MsgInMsgBase
from os_ken.ofproto import ether
from os_ken.ofproto import nicira_ext
from os_ken.ofproto import nx_actions
from os_ken.ofproto import ofproto_parser
from os_ken.ofproto import ofproto_common
@ -53,6 +54,15 @@ def _register_parser(cls):
return cls
def _register_exp_type(experimenter, exp_type):
assert exp_type not in OFPExperimenter._subtypes
def _wrapper(cls):
OFPExperimenter._subtypes[(experimenter, exp_type)] = cls
return cls
return _wrapper
@ofproto_parser.register_msg_parser(ofproto.OFP_VERSION)
def msg_parser(datapath, version, msg_type, msg_len, xid, buf):
parser = _MSG_PARSERS.get(msg_type)
@ -407,6 +417,7 @@ class OFPExperimenter(MsgBase):
data Experimenter defined arbitrary additional data
============= =========================================================
"""
_subtypes = {}
def __init__(self, datapath, experimenter=None, exp_type=None, data=None):
super(OFPExperimenter, self).__init__(datapath)
@ -423,6 +434,13 @@ class OFPExperimenter(MsgBase):
ofproto.OFP_EXPERIMENTER_HEADER_PACK_STR, msg.buf,
ofproto.OFP_HEADER_SIZE)
msg.data = msg.buf[ofproto.OFP_EXPERIMENTER_HEADER_SIZE:]
if (msg.experimenter, msg.exp_type) in cls._subtypes:
new_msg = cls._subtypes[
(msg.experimenter, msg.exp_type)].parser_subtype(msg)
new_msg.set_headers(msg.version, msg.msg_type, msg.msg_len,
msg.xid)
new_msg.set_buf(msg.buf)
return new_msg
return msg
@ -6934,6 +6952,169 @@ class OFPBundleAddMsg(MsgInMsgBase):
self.buf += tail_buf
@_register_exp_type(ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_SET_PACKET_IN_FORMAT)
class NXTSetPacketInFormatMsg(OFPExperimenter):
def __init__(self, datapath, packet_in_format):
super(NXTSetPacketInFormatMsg, self).__init__(
datapath, ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_SET_PACKET_IN_FORMAT)
self.packet_in_format = packet_in_format
def _serialize_body(self):
msg_pack_into(ofproto.OFP_EXPERIMENTER_HEADER_PACK_STR,
self.buf, ofproto.OFP_HEADER_SIZE,
self.experimenter, self.exp_type)
msg_pack_into(nicira_ext.NX_SET_PACKET_IN_FORMAT_PACK_STR,
self.buf, ofproto.OFP_EXPERIMENTER_HEADER_SIZE,
self.packet_in_format)
@classmethod
def parser_subtype(cls, super_msg):
packet_in_format = struct.unpack_from(
nicira_ext.NX_SET_PACKET_IN_FORMAT_PACK_STR, super_msg.data)[0]
msg = cls(super_msg.datapath, packet_in_format)
msg.properties = []
return msg
@_register_exp_type(ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_PACKET_IN2)
class NXTPacketIn2(OFPExperimenter):
def __init__(self, datapath, properties=None):
super(NXTPacketIn2, self).__init__(
datapath, ofproto_common.NX_EXPERIMENTER_ID,
nicira_ext.NXT_PACKET_IN2)
self.properties = properties or []
self.data = None
self.total_len = None
self.buffer_id = None
self.table_id = None
self.cookie = None
self.reason = None
self.metadata = None
self.userdata = None
self.continuation = None
def _serialize_body(self):
bin_props = bytearray()
for p in self.properties:
bin_props += p.serialize()
msg_pack_into(ofproto.OFP_EXPERIMENTER_HEADER_PACK_STR,
self.buf, ofproto.OFP_HEADER_SIZE,
self.experimenter, self.exp_type)
self.buf += bin_props
@classmethod
def parser_subtype(cls, super_msg):
msg = cls(super_msg.datapath)
rest = super_msg.data
while rest:
p, rest = NXTPacketIn2Prop.parse(rest)
msg.properties.append(p)
msg._parse_property(p)
return msg
def _parse_property(self, p):
if p.type == nicira_ext.NXPINT_PACKET:
self.data = p.data
# Note: here total_len is length of packet but not msg
self.total_len = p.length
elif p.type == nicira_ext.NXPINT_FULL_LEN:
self.total_len = struct.unpack_from('!I', p.data)[0]
elif p.type == nicira_ext.NXPINT_BUFFER_ID:
self.buffer_id = struct.unpack_from('!I', p.data)[0]
elif p.type == nicira_ext.NXPINT_TABLE_ID:
self.table_id = struct.unpack_from('B', p.data)[0]
elif p.type == nicira_ext.NXPINT_COOKIE:
self.cookie = struct.unpack_from('!Q', p.data)[0]
elif p.type == nicira_ext.NXPINT_REASON:
self.reason = struct.unpack_from('!B', p.data)[0]
elif p.type == nicira_ext.NXPINT_METADATA:
self.metadata = p.data
elif p.type == nicira_ext.NXPINT_USERDATA:
self.userdata = p.data
elif p.type == nicira_ext.NXPINT_CONTINUATION:
self.continuation = p.data
class NXTPacketIn2Prop(OFPPropBase):
_TYPES = {}
_PROP_TYPE = None
def __init__(self, type_=None, length=None, data=None):
super(NXTPacketIn2Prop, self).__init__(type_, length)
self.data = data
@classmethod
def parse(cls, buf):
(type_, length) = struct.unpack_from(cls._PACK_STR, buf, 0)
rest = buf[utils.round_up(length, 8):]
try:
subcls = cls._TYPES[type_]
except KeyError:
subcls = OFPPropUnknown
prop = subcls.sub_parser(buf, type, length)
prop.type = type_
prop.length = length
return prop, rest
def serialize_body(self):
return self.data
@classmethod
def sub_parser(cls, buf, type, length):
p = cls(type, length - 4, buf[4:length])
return p
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_PACKET)
class NXTPacketIn2PropPacket(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_PACKET
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_FULL_LEN)
class NXTPacketIn2PropFullLen(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_FULL_LEN
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_BUFFER_ID)
class NXTPacketIn2PropBufferId(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_BUFFER_ID
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_TABLE_ID)
class NXTPacketIn2PropTableId(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_TABLE_ID
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_COOKIE)
class NXTPacketIn2PropCookie(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_COOKIE
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_REASON)
class NXTPacketIn2PropReason(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_REASON
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_METADATA)
class NXTPacketIn2PropMetadata(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_METADATA
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_USERDATA)
class NXTPacketIn2PropUserData(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_USERDATA
@NXTPacketIn2Prop.register_type(nicira_ext.NXPINT_CONTINUATION)
class NXTPacketIn2PropContinuation(NXTPacketIn2Prop):
_PROP_TYPE = nicira_ext.NXPINT_CONTINUATION
nx_actions.generate(
'os_ken.ofproto.ofproto_v1_5',
'os_ken.ofproto.ofproto_v1_5_parser'