
# Copyright 2017-present Open Networking Foundation
#
# 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.


"""
Test cases for testing actions taken on packets

See basic.py for other info.

It is recommended that these definitions be kept in their own
namespace as different groups of tests will likely define 
similar identifiers.

The switch is actively attempting to contact the controller at the address
indicated in config.

"""

import copy
import logging
import time
import unittest
import random
import oftest.packet as scapy

from oftest import config
import oftest.controller as controller
import ofp
import oftest.dataplane as dataplane
import oftest.parse as parse
import oftest.base_tests as base_tests
import basic # for IterCases

from oftest.parse import parse_mac, parse_ip

from oftest.testutils import *

WILDCARD_VALUES = [ofp.OFPFW_IN_PORT,
                   ofp.OFPFW_DL_VLAN | ofp.OFPFW_DL_VLAN_PCP,
                   ofp.OFPFW_DL_SRC,
                   ofp.OFPFW_DL_DST,
                   (ofp.OFPFW_DL_TYPE | ofp.OFPFW_NW_SRC_ALL |
                    ofp.OFPFW_NW_DST_ALL | ofp.OFPFW_NW_TOS | ofp.OFPFW_NW_PROTO |
                    ofp.OFPFW_TP_SRC | ofp.OFPFW_TP_DST),
                   (ofp.OFPFW_NW_PROTO | ofp.OFPFW_TP_SRC | ofp.OFPFW_TP_DST),
                   ofp.OFPFW_TP_SRC,
                   ofp.OFPFW_TP_DST,
                   ofp.OFPFW_NW_SRC_MASK,
                   ofp.OFPFW_NW_DST_MASK,
                   ofp.OFPFW_DL_VLAN_PCP,
                   ofp.OFPFW_NW_TOS]

NO_WILDCARD_VALUES = [(ofp.OFPFW_ALL ^ ofp.OFPFW_IN_PORT),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_VLAN),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_SRC),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_DST),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_TYPE),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_TYPE ^ ofp.OFPFW_NW_PROTO),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_TYPE ^ ofp.OFPFW_NW_PROTO ^
                       ofp.OFPFW_TP_SRC),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_TYPE ^ ofp.OFPFW_NW_PROTO ^
                       ofp.OFPFW_TP_DST),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_TYPE ^ ofp.OFPFW_NW_PROTO ^
                       ofp.OFPFW_NW_SRC_MASK),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_TYPE ^ ofp.OFPFW_NW_PROTO ^
                       ofp.OFPFW_NW_DST_MASK),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_VLAN ^ ofp.OFPFW_DL_VLAN_PCP),
                      (ofp.OFPFW_ALL ^ ofp.OFPFW_DL_TYPE ^ ofp.OFPFW_NW_PROTO ^
                       ofp.OFPFW_NW_TOS)]

MODIFY_ACTION_VALUES =  [ofp.OFPAT_SET_VLAN_VID,
                         ofp.OFPAT_SET_VLAN_PCP,
                         ofp.OFPAT_STRIP_VLAN,
                         ofp.OFPAT_SET_DL_SRC,
                         ofp.OFPAT_SET_DL_DST,
                         ofp.OFPAT_SET_NW_SRC,
                         ofp.OFPAT_SET_NW_DST,
                         ofp.OFPAT_SET_NW_TOS,
                         ofp.OFPAT_SET_TP_SRC,
                         ofp.OFPAT_SET_TP_DST]

TEST_VID_DEFAULT = 2

@group('smoke')
class DirectPacket(base_tests.SimpleDataPlane):
    """
    Send packet to single egress port

    Generate a packet
    Generate and install a matching flow
    Add action to direct the packet to an egress port
    Send the packet to ingress dataplane port
    Verify the packet is received at the egress port only
    """
    def runTest(self):
        self.handleFlow()

    def handleFlow(self, pkttype='TCP'):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        if (pkttype == 'ICMP'):
            pkt = simple_icmp_packet()
        else:
            pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")
        act = ofp.action.output()

        for idx in range(len(of_ports)):
            delete_all_flows(self.controller)

            ingress_port = of_ports[idx]
            egress_port = of_ports[(idx + 1) % len(of_ports)]
            logging.info("Ingress " + str(ingress_port) + 
                             " to egress " + str(egress_port))

            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match

            request.buffer_id = 0xffffffff
            act.port = egress_port
            request.actions.append(act)

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + 
                           str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))

            exp_pkt_arg = None
            exp_port = None
            if config["relax"]:
                exp_pkt_arg = pkt
                exp_port = egress_port

            (rcv_port, rcv_pkt, pkt_time) = self.dataplane.poll(port_number=exp_port,
                                                                exp_pkt=exp_pkt_arg)
            self.assertTrue(rcv_pkt is not None, "Did not receive packet")
            logging.debug("Packet len " + str(len(rcv_pkt)) + " in on " + 
                         str(rcv_port))
            self.assertEqual(rcv_port, egress_port, "Unexpected receive port")
            self.assertEqual(str(pkt), str(rcv_pkt),
                             'Response packet does not match send packet')

@group('smoke')
class DirectPacketController(base_tests.SimpleDataPlane):
    """
    Send packet to the controller port

    Generate a packet
    Generate and install a matching flow
    Add action to direct the packet to the controller port
    Send the packet to ingress dataplane port
    Verify the packet is received at the controller port
    """
    def runTest(self):
        self.handleFlow()

    def handleFlow(self, pkttype='TCP'):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 0, "Not enough ports for test")

        if (pkttype == 'ICMP'):
            pkt = simple_icmp_packet()
        else:
            pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None,
                        "Could not generate flow match from pkt")
        act = ofp.action.output()

        delete_all_flows(self.controller)

        ingress_port = of_ports[0]
        match.in_port = ingress_port

        request = ofp.message.flow_add()
        request.match = match

        request.buffer_id = 0xffffffff
        act.port = ofp.OFPP_CONTROLLER
        act.max_len = 65535
        request.actions.append(act)

        logging.info("Inserting flow")
        self.controller.message_send(request)
        do_barrier(self.controller)

        logging.info("Sending packet to dp port " +
                        str(ingress_port))
        self.dataplane.send(ingress_port, str(pkt))

        verify_packet_in(self, str(pkt), ingress_port, ofp.OFPR_ACTION)

class DirectPacketQueue(base_tests.SimpleDataPlane):
    """
    Send packet to single queue on single egress port

    Generate a packet
    Generate and install a matching flow
    Add action to direct the packet to an egress port and queue
    Send the packet to ingress dataplane port
    Verify the packet is received at the egress port only
    """
    def runTest(self):
        self.handleFlow()

    def portQueuesGet(self, queue_stats, port_num):
        result = []
        for qs in queue_stats.entries:
            if qs.port_no != port_num:
                continue
            result.append(qs.queue_id)
        return result

    def handleFlow(self, pkttype='TCP'):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        if (pkttype == 'ICMP'):
            pkt = simple_icmp_packet()
        else:
            pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")

        # Get queue stats from switch
        
        request = ofp.message.queue_stats_request()
        request.port_no  = ofp.OFPP_ALL
        request.queue_id = ofp.OFPQ_ALL
        (queue_stats, p) = self.controller.transact(request)
        self.assertNotEqual(queue_stats, None, "Queue stats request failed")

        act = ofp.action.enqueue()

        for idx in range(len(of_ports)):
            ingress_port = of_ports[idx]
            egress_port = of_ports[(idx + 1) % len(of_ports)]

            for egress_queue_id in self.portQueuesGet(queue_stats, egress_port):
                logging.info("Ingress " + str(ingress_port)
                               + " to egress " + str(egress_port)
                               + " queue " + str(egress_queue_id)
                               )

                delete_all_flows(self.controller)

                match.in_port = ingress_port
                
                request = ofp.message.flow_add()
                request.match = match

                request.buffer_id = 0xffffffff
                act.port     = egress_port
                act.queue_id = egress_queue_id
                request.actions.append(act)

                logging.info("Inserting flow")
                self.controller.message_send(request)
                do_barrier(self.controller)

                # Get current stats for selected egress queue

                request = ofp.message.queue_stats_request()
                request.port_no  = egress_port
                request.queue_id = egress_queue_id
                (qs_before, p) = self.controller.transact(request)
                self.assertNotEqual(qs_before, None, "Queue stats request failed")

                logging.info("Sending packet to dp port " + 
                               str(ingress_port))
                self.dataplane.send(ingress_port, str(pkt))
                
                exp_pkt_arg = None
                exp_port = None
                if config["relax"]:
                    exp_pkt_arg = pkt
                    exp_port = egress_port
                    
                    (rcv_port, rcv_pkt, pkt_time) = self.dataplane.poll(port_number=exp_port,
                                                                        exp_pkt=exp_pkt_arg)
                    self.assertTrue(rcv_pkt is not None, "Did not receive packet")
                    logging.debug("Packet len " + str(len(rcv_pkt)) + " in on " + 
                                    str(rcv_port))
                    self.assertEqual(rcv_port, egress_port, "Unexpected receive port")
                    self.assertEqual(str(pkt), str(rcv_pkt),
                                     'Response packet does not match send packet')

                # FIXME: instead of sleeping, keep requesting queue stats until
                # the expected queue counter increases or some large timeout is
                # reached
                time.sleep(2)

                # Get current stats for selected egress queue again

                request = ofp.message.queue_stats_request()
                request.port_no  = egress_port
                request.queue_id = egress_queue_id
                (qs_after, p) = self.controller.transact(request)
                self.assertNotEqual(qs_after, None, "Queue stats request failed")

                # Make sure that tx packet counter for selected egress queue was
                # incremented

                self.assertEqual(qs_after.entries[0].tx_packets, \
                                 qs_before.entries[0].tx_packets + 1, \
                                 "Verification of egress queue tx packet count failed"
                                 )
                    

class DirectPacketControllerQueue(base_tests.SimpleDataPlane):
    """
    Send a packet from each of the openflow ports
    to each of the queues configured on the controller port.
    If no queues have been configured, no packets are sent.

    Generate a packet
    Generate and install a matching flow
    Add action to direct the packet to one of the controller port queues
    Send the packet to ingress dataplane port
    Verify the packet is received on the controller port queue
    """
    def runTest(self):
        self.handleFlow()

    def portQueuesGet(self, queue_stats, port_num):
        result = []
        for qs in queue_stats.entries:
            if qs.port_no != port_num:
                continue
            result.append(qs.queue_id)
        return result

    def handleFlow(self, pkttype='TCP'):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        if (pkttype == 'ICMP'):
            pkt = simple_icmp_packet()
        else:
            pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")

        # Get queue stats from switch
        
        request = ofp.message.queue_stats_request()
        request.port_no  = ofp.OFPP_CONTROLLER
        request.queue_id = ofp.OFPQ_ALL
        (queue_stats, p) = self.controller.transact(request)
        self.assertNotEqual(queue_stats, None, "Queue stats request failed")
        if queue_stats.type == ofp.OFPT_ERROR:
            skip_message_emit(self, "Enqueue packet to controller")
            return

        act = ofp.action.enqueue()

        for idx in range(len(of_ports)):
            ingress_port = of_ports[idx]
            egress_port = ofp.OFPP_CONTROLLER

            logging.info("Ingress port " + str(ingress_port)
                           + ", controller port queues " 
                           + str(self.portQueuesGet(queue_stats, egress_port)))

            for egress_queue_id in self.portQueuesGet(queue_stats, egress_port):
                logging.info("Ingress " + str(ingress_port)
                               + " to egress " + str(egress_port)
                               + " queue " + str(egress_queue_id)
                               )

                delete_all_flows(self.controller)

                match.in_port = ingress_port
                
                request = ofp.message.flow_add()
                request.match = match

                request.buffer_id = 0xffffffff
                act.port     = egress_port
                act.queue_id = egress_queue_id
                request.actions.append(act)

                logging.info("Inserting flow")
                self.controller.message_send(request)
                do_barrier(self.controller)

                # Get current stats for selected egress queue

                request = ofp.message.queue_stats_request()
                request.port_no  = egress_port
                request.queue_id = egress_queue_id
                (qs_before, p) = self.controller.transact(request)
                self.assertNotEqual(qs_before, None, "Queue stats request failed")

                logging.info("Sending packet to dp port " + 
                               str(ingress_port))
                self.dataplane.send(ingress_port, str(pkt))

                verify_packet_in(self, str(pkt), ingress_port, ofp.OFPR_ACTION)

                # FIXME: instead of sleeping, keep requesting queue stats until
                # the expected queue counter increases or some large timeout is
                # reached
                time.sleep(2)

                # Get current stats for selected egress queue again

                request = ofp.message.queue_stats_request()
                request.port_no  = egress_port
                request.queue_id = egress_queue_id
                (qs_after, p) = self.controller.transact(request)
                self.assertNotEqual(qs_after, None, "Queue stats request failed")

                # Make sure that tx packet counter for selected egress queue was
                # incremented

                self.assertEqual(qs_after.entries[0].tx_packets, \
                                 qs_before.entries[0].tx_packets + 1, \
                                 "Verification of egress queue tx packet count failed"
                                 )
                    

class DirectPacketICMP(DirectPacket):
    """
    Send ICMP packet to single egress port

    Generate a ICMP packet
    Generate and install a matching flow
    Add action to direct the packet to an egress port
    Send the packet to ingress dataplane port
    Verify the packet is received at the egress port only
    Difference from DirectPacket test is that sent packet is ICMP
    """
    def runTest(self):
        self.handleFlow(pkttype='ICMP')

class DirectTwoPorts(base_tests.SimpleDataPlane):
    """
    Send packet to two egress ports

    Generate a packet
    Generate and install a matching flow
    Add action to direct the packet to two egress ports
    Send the packet to ingress dataplane port
    Verify the packet is received at the two egress ports
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 2, "Not enough ports for test")

        pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")

        for idx in range(len(of_ports)):
            delete_all_flows(self.controller)

            ingress_port = of_ports[idx]
            egress_port1 = of_ports[(idx + 1) % len(of_ports)]
            egress_port2 = of_ports[(idx + 2) % len(of_ports)]
            logging.info("Ingress " + str(ingress_port) + 
                           " to egress " + str(egress_port1) + " and " +
                           str(egress_port2))

            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match
            request.buffer_id = 0xffffffff
            request.actions.append(ofp.action.output(port=egress_port1))
            request.actions.append(ofp.action.output(port=egress_port2))
            # logging.info(request.show())

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + 
                           str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))
            verify_packets(self, pkt, [egress_port1, egress_port2])

class DirectMCNonIngress(base_tests.SimpleDataPlane):
    """
    Multicast to all non-ingress ports

    Generate a packet
    Generate and install a matching flow
    Add action to direct the packet to all non-ingress ports
    Send the packet to ingress dataplane port
    Verify the packet is received at all non-ingress ports

    Does not use the flood action
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 2, "Not enough ports for test")

        pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")

        for ingress_port in of_ports:
            delete_all_flows(self.controller)

            logging.info("Ingress " + str(ingress_port) + 
                           " all non-ingress ports")
            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match
            request.buffer_id = 0xffffffff
            for egress_port in of_ports:
                if egress_port == ingress_port:
                    continue
                request.actions.append(ofp.action.output(port=egress_port))
            logging.debug(request.show())

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))
            yes_ports = set(of_ports).difference([ingress_port])
            verify_packets(self, pkt, yes_ports)


class DirectMC(base_tests.SimpleDataPlane):
    """
    Multicast to all ports including ingress

    Generate a packet
    Generate and install a matching flow
    Add action to direct the packet to all non-ingress ports
    Send the packet to ingress dataplane port
    Verify the packet is received at all ports

    Does not use the flood action
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 2, "Not enough ports for test")

        pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")

        for ingress_port in of_ports:
            delete_all_flows(self.controller)

            logging.info("Ingress " + str(ingress_port) + " to all ports")
            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match
            request.buffer_id = 0xffffffff
            for egress_port in of_ports:
                act = ofp.action.output()
                if egress_port == ingress_port:
                    act.port = ofp.OFPP_IN_PORT
                else:
                    act.port = egress_port
                request.actions.append(act)
            # logging.info(request.show())

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))
            verify_packets(self, pkt, of_ports)

class Flood(base_tests.SimpleDataPlane):
    """
    Flood to all ports except ingress

    Make sure noflood bit is off on all ports
    Generate a packet
    Generate and install a matching flow
    Add action to flood the packet
    Send the packet to ingress dataplane port
    Verify the packet is received at all other ports
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")
        act = ofp.action.output()

        for of_port in of_ports:
            # Clear relevant bits that might block ports
            rv = port_config_set(self.controller, of_port, 0,
                                 ofp.OFPPC_NO_FLOOD | ofp.OFPPC_NO_FWD |
                                 ofp.OFPPC_PORT_DOWN)
            self.assertTrue(rv == 0, "Did not set port config")
            logging.debug("Enabled and cleared no-flood for port " + str(of_port))

        for ingress_port in of_ports:
            delete_all_flows(self.controller)

            logging.info("Ingress " + str(ingress_port) + " to all ports")
            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match
            request.buffer_id = 0xffffffff
            act.port = ofp.OFPP_FLOOD
            request.actions.append(act)
            logging.info(request.show())

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))
            yes_ports = set(of_ports).difference([ingress_port])
            verify_packets(self, pkt, yes_ports)

class FloodPlusIngress(base_tests.SimpleDataPlane):
    """
    Flood to all ports plus send to ingress port

    Generate a packet
    Generate and install a matching flow
    Add action to flood the packet
    Add action to send to ingress port
    Send the packet to ingress dataplane port
    Verify the packet is received at all other ports
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")

        for ingress_port in of_ports:
            delete_all_flows(self.controller)

            logging.info("Ingress " + str(ingress_port) + " to all ports")
            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match
            request.buffer_id = 0xffffffff
            request.actions.append(ofp.action.output(port=ofp.OFPP_FLOOD))
            request.actions.append(ofp.action.output(port=ofp.OFPP_IN_PORT))
            logging.info(request.show())

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))
            verify_packets(self, pkt, of_ports)

class All(base_tests.SimpleDataPlane):
    """
    Send to OFPP_ALL port

    Generate a packet
    Generate and install a matching flow
    Add action to forward to OFPP_ALL
    Send the packet to ingress dataplane port
    Verify the packet is received at all other ports
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")
        act = ofp.action.output()

        for ingress_port in of_ports:
            delete_all_flows(self.controller)

            logging.info("Ingress " + str(ingress_port) + " to all ports")
            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match
            request.buffer_id = 0xffffffff
            act.port = ofp.OFPP_ALL
            request.actions.append(act)
            logging.info(request.show())

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))
            yes_ports = set(of_ports).difference([ingress_port])
            verify_packets(self, pkt, yes_ports)

class AllPlusIngress(base_tests.SimpleDataPlane):
    """
    Send to OFPP_ALL port and ingress port

    Generate a packet
    Generate and install a matching flow
    Add action to forward to OFPP_ALL
    Add action to forward to ingress port
    Send the packet to ingress dataplane port
    Verify the packet is received at all other ports
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")

        for ingress_port in of_ports:
            delete_all_flows(self.controller)

            logging.info("Ingress " + str(ingress_port) + " to all ports")
            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match
            request.buffer_id = 0xffffffff
            request.actions.append(ofp.action.output(port=ofp.OFPP_ALL))
            request.actions.append(ofp.action.output(port=ofp.OFPP_IN_PORT))
            logging.info(request.show())

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))
            verify_packets(self, pkt, of_ports)
            
class FloodMinusPort(base_tests.SimpleDataPlane):
    """
    Config port with No_Flood and test Flood action

    Generate a packet
    Generate a matching flow
    Add action to forward to OFPP_ALL
    Set port to no-flood
    Send the packet to ingress dataplane port
    Verify the packet is received at all other ports except
    the ingress port and the no_flood port
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 2, "Not enough ports for test")

        pkt = simple_tcp_packet()
        match = packet_to_flow_match(self, pkt)
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")
        act = ofp.action.output()

        # Clear OFPPC_NO_FLOOD on each port
        for of_port in of_ports:
            rv = port_config_set(self.controller, of_port,
                                 0, ofp.OFPPC_NO_FLOOD)
            self.assertEqual(rv, 0, "Failed to set port config")

        for idx in range(len(of_ports)):
            delete_all_flows(self.controller)

            ingress_port = of_ports[idx]
            no_flood_idx = (idx + 1) % len(of_ports)
            no_flood_port = of_ports[no_flood_idx]
            rv = port_config_set(self.controller, no_flood_port,
                                 ofp.OFPPC_NO_FLOOD, ofp.OFPPC_NO_FLOOD)
            self.assertEqual(rv, 0, "Failed to set port config")

            match.in_port = ingress_port

            request = ofp.message.flow_add()
            request.match = match
            request.buffer_id = 0xffffffff
            act.port = ofp.OFPP_FLOOD
            request.actions.append(act)
            logging.info(request.show())

            logging.info("Inserting flow")
            self.controller.message_send(request)
            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + str(ingress_port))
            logging.info("No flood port is " + str(no_flood_port))
            self.dataplane.send(ingress_port, str(pkt))
            no_ports = set([ingress_port, no_flood_port])
            yes_ports = set(of_ports).difference(no_ports)
            verify_packets(self, pkt, yes_ports)

            # Turn no flood off again
            rv = port_config_set(self.controller, no_flood_port,
                                 0, ofp.OFPPC_NO_FLOOD)
            self.assertEqual(rv, 0, "Failed to reset port config")
            do_barrier(self.controller)

            # Check that packets are now flooded to no_flood_port
            logging.info("Sending packet to dp port " + str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))
            no_ports = set([ingress_port])
            yes_ports = set(of_ports).difference(no_ports)
            verify_packets(self, pkt, yes_ports)

            #@todo Should check no other packets received



################################################################

class BaseMatchCase(base_tests.SimpleDataPlane):
    def setUp(self):
        base_tests.SimpleDataPlane.setUp(self)
    def runTest(self):
        logging.info("BaseMatchCase")

class ExactMatch(BaseMatchCase):
    """
    Exercise exact matching for all port pairs

    Generate a packet
    Generate and install a matching flow without wildcard mask
    Add action to forward to a port
    Send the packet to the port
    Verify the packet is received at all other ports (one port at a time)
    """

    def runTest(self):
        flow_match_test(self, config["port_map"])

class ExactMatchTagged(BaseMatchCase):
    """
    Exact match for all port pairs with tagged pkts
    """

    def runTest(self):
        vid = test_param_get('vid', default=TEST_VID_DEFAULT)
        flow_match_test(self, config["port_map"], vlan_vid=vid)

@disabled
class ExactMatchTaggedMany(BaseMatchCase):
    """
    ExactMatchTagged with many VLANS
    """

    def runTest(self):
        for vid in range(2,100,10):
            flow_match_test(self, config["port_map"], vlan_vid=vid, max_test=5)
        for vid in range(100,4000,389):
            flow_match_test(self, config["port_map"], vlan_vid=vid, max_test=5)
        flow_match_test(self, config["port_map"], vlan_vid=4094, max_test=5)

class SingleWildcardMatchPriority(BaseMatchCase):
    """
    SingleWildcardMatchPriority
    """

    def _Init(self):
        self.pkt = simple_tcp_packet()
        self.flowMsgs = {}

    def _ClearTable(self):
        delete_all_flows(self.controller)
        do_barrier(self.controller)

    def runTest(self):
        
        self._Init()
        of_ports = config["port_map"].keys()
        of_ports.sort()

        # Delete the initial flow table
        self._ClearTable()

        # Run several combinations, each at lower priority settings. 
        # At the end of each call to runPrioFlows(), the table should
        # be empty. If its not, we'll catch it as the priorities decreases
        portA = of_ports[0]
        portB = of_ports[1]
        portC = of_ports[2]

        # TODO -- these priority numbers should be validated somehow?
        self.runPrioFlows(portA, portB, portC, 1000, 999)
        self.runPrioFlows(portB, portC, portA, 998, 997)
        self.runPrioFlows(portC, portA, portB, 996, 995)
        self.runPrioFlows(portA, portC, portB, 994, 993)


    
    def runPrioFlows(self, portA, portB, portC, prioHigher, prioLower, 
                     clearTable=False):

        if clearTable:
            self._ClearTable()

        # Sanity check flow at lower priority from pA to pB
        logging.info("runPrioFlows(pA=%d,pB=%d,pC=%d,ph=%d,pl=%d"
                         % (portA, portB, portC, prioHigher, prioLower))

        # Sanity check flow at lower priority from pA to pC
        self.installFlow(prioLower, portA, portC)
        self.verifyFlow(portA, portC)
        self.removeFlow(prioLower)

        # Install and verify pA->pB @ prioLower
        self.installFlow(prioLower, portA, portB)
        self.verifyFlow(portA, portB)

        # Install and verify pA->pC @ prioHigher, should override pA->pB
        self.installFlow(prioHigher, portA, portC)
        self.verifyFlow(portA, portC)
        # remove pA->pC
        self.removeFlow(prioHigher)
        # Old flow pA -> pB @ prioLower should still be active
        self.verifyFlow(portA, portB)
        self.removeFlow(prioLower)

        # Table should be empty at this point, leave it alone as
        # an assumption for future test runs



    def installFlow(self, prio, inp, egp,
                    wildcards=ofp.OFPFW_DL_SRC):
        wildcards |= required_wildcards(self)
        request = flow_msg_create(self, self.pkt, ing_port=inp, 
                                  wildcards=wildcards,
                                  egr_ports=egp)
        request.priority = prio
        logging.debug("Install flow with priority " + str(prio))
        flow_msg_install(self, request, clear_table_override=False)
        self.flowMsgs[prio] = request
        
    def removeFlow(self, prio):
        if self.flowMsgs.has_key(prio):
            old_msg = self.flowMsgs[prio]
            msg = ofp.message.flow_delete_strict(out_port=ofp.OFPP_NONE,
                                                 match=old_msg.match,
                                                 priority=old_msg.priority)
            logging.debug("Remove flow with priority " + str(prio))
            self.controller.message_send(msg)
            do_barrier(self.controller)
        else:
            raise Exception("Not initialized")


    def verifyFlow(self, inp, egp, pkt=None):
        if pkt == None:
            pkt = self.pkt

        logging.info("Pkt match test: " + str(inp) + " to " + str(egp))
        logging.debug("Send packet: " + str(inp) + " to " + str(egp))
        self.dataplane.send(inp, str(pkt))
        verify_packets(self, pkt, [egp])


       
class SingleWildcardMatchPriorityInsertModifyDelete(SingleWildcardMatchPriority):

    def runTest(self):

        self._Init()

        of_ports = config["port_map"].keys()
        of_ports.sort()

        # Install an entry from 0 -> 1 @ prio 1000
        self._ClearTable()
        self.installFlow(1000, of_ports[0], of_ports[1])
        self.verifyFlow(of_ports[0], of_ports[1])
        self.installFlow(1000, of_ports[1], of_ports[0])
        self.verifyFlow(of_ports[1], of_ports[0])
        self.installFlow(1001, of_ports[0], of_ports[1])
        self.verifyFlow(of_ports[0], of_ports[1])
        self.installFlow(1001, of_ports[1], of_ports[0])
        self.verifyFlow(of_ports[1], of_ports[0])
        self.removeFlow(1001)
        self.verifyFlow(of_ports[0], of_ports[1])
        self.removeFlow(1000)



class WildcardPriority(SingleWildcardMatchPriority):
    """
    1. Add wildcard flow, verify packet received.
    2. Add wildcard flow with higher priority, verify packet received
    on port specified by this flow.
    3. Add wildcard flow with lower priority, verify packet received
    on port specified by the highest priority flow.
    """

    def runTest(self):
        
        self._Init()

        of_ports = config["port_map"].keys()
        of_ports.sort()

        self._ClearTable()

        # Install a flow with wildcards
        self.installFlow(999, of_ports[0], of_ports[1], 
                         wildcards=ofp.OFPFW_DL_DST)
        self.verifyFlow(of_ports[0], of_ports[1])
        # Install a flow with wildcards with higher priority
        self.installFlow(1000, of_ports[0], of_ports[2],
                         wildcards=ofp.OFPFW_DL_DST)
        self.verifyFlow(of_ports[0], of_ports[2])
        # Install a flow with wildcards with lower priority
        self.installFlow(999, of_ports[0], of_ports[1],
                         wildcards=ofp.OFPFW_DL_SRC)
        self.verifyFlow(of_ports[0], of_ports[2])
        

@group("smoke")
class WildcardPriorityWithDelete(SingleWildcardMatchPriority):
    """
    1. Add wildcard match flow, verify packet received.
    2. Add wildcard flow with higher priority, verify packet received on port
    specified by this flow.
    3. Add wildcard flow with even higher priority, verify packet received
    on port specified by this flow.
    4. Delete lowest priority flow, verify packet received on port specified
    by highest priority flow.
    5. Delete highest priority flow, verify packet received on port specified
    by remaining flow.
    """

    def runTest(self):
        
        self._Init()

        of_ports = config["port_map"].keys()
        of_ports.sort()

        self._ClearTable()

        # Install a flow with wildcards
        self.installFlow(250, of_ports[0], of_ports[1],
                         wildcards=ofp.OFPFW_DL_DST)
        self.verifyFlow(of_ports[0], of_ports[1])
        # Install a flow with wildcards of higher priority
        self.installFlow(1250, of_ports[0], of_ports[2],
                         wildcards=ofp.OFPFW_DL_DST)
        self.verifyFlow(of_ports[0], of_ports[2])
        # Install a flow with wildcards with even higher priority
        self.installFlow(2001, of_ports[0], of_ports[3],
                         wildcards=ofp.OFPFW_DL_DST)
        self.verifyFlow(of_ports[0], of_ports[3])
        # Delete lowest priority flow
        self.removeFlow(250)
        self.verifyFlow(of_ports[0], of_ports[3])
        # Delete highest priority flow
        self.removeFlow(2001)
        self.verifyFlow(of_ports[0], of_ports[2])
        

class SingleWildcardMatch(BaseMatchCase):
    """
    Exercise wildcard matching for all ports

    Generate a packet
    Generate and install a matching flow with wildcard mask
    Add action to forward to a port
    Send the packet to the port
    Verify the packet is received at all other ports (one port at a time)
    Verify flow_expiration message is correct when command option is set
    """
    def runTest(self):
        vid = test_param_get('vid', default=TEST_VID_DEFAULT)
        for wc in WILDCARD_VALUES:
            wc |= required_wildcards(self)
            if wc & ofp.OFPFW_DL_VLAN:
                # Set nonzero VLAN id to avoid sending priority-tagged packet
                vlan_vid = vid
            else:
                vlan_vid = -1
            flow_match_test(self, config["port_map"], wildcards=wc, 
                            vlan_vid=vlan_vid, max_test=10)

class SingleWildcardMatchTagged(BaseMatchCase):
    """
    SingleWildcardMatch with tagged packets
    """
    def runTest(self):
        vid = test_param_get('vid', default=TEST_VID_DEFAULT)
        for wc in WILDCARD_VALUES:
            wc |= required_wildcards(self)
            flow_match_test(self, config["port_map"], wildcards=wc, vlan_vid=vid,
                            max_test=10)

class AllExceptOneWildcardMatch(BaseMatchCase):
    """
    Match exactly one field

    Generate a packet
    Generate and install a matching flow with wildcard all except one filed
    Add action to forward to a port
    Send the packet to the port
    Verify the packet is received at all other ports (one port at a time)
    Verify flow_expiration message is correct when command option is set
    """
    def runTest(self):
        vid = test_param_get('vid', default=TEST_VID_DEFAULT)
        for all_exp_one_wildcard in NO_WILDCARD_VALUES:
            all_exp_one_wildcard |= required_wildcards(self)
            if all_exp_one_wildcard & ofp.OFPFW_DL_VLAN:
                # Set nonzero VLAN id to avoid sending priority-tagged packet
                vlan_vid = vid
            else:
                vlan_vid = -1
            flow_match_test(self, config["port_map"], wildcards=all_exp_one_wildcard,
                            vlan_vid=vlan_vid)

class AllExceptOneWildcardMatchTagged(BaseMatchCase):
    """
    Match one field with tagged packets
    """
    def runTest(self):
        vid = test_param_get('vid', default=TEST_VID_DEFAULT)
        for all_exp_one_wildcard in NO_WILDCARD_VALUES:
            all_exp_one_wildcard |= required_wildcards(self)
            flow_match_test(self, config["port_map"], wildcards=all_exp_one_wildcard,
                            vlan_vid=vid)

class AllWildcardMatch(BaseMatchCase):
    """
    Create Wildcard-all flow and exercise for all ports

    Generate a packet
    Generate and install a matching flow with wildcard-all
    Add action to forward to a port
    Send the packet to the port
    Verify the packet is received at all other ports (one port at a time)
    Verify flow_expiration message is correct when command option is set
    """
    def runTest(self):
        flow_match_test(self, config["port_map"], wildcards=ofp.OFPFW_ALL)

class AllWildcardMatchTagged(BaseMatchCase):
    """
    AllWildcardMatch with tagged packets
    """
    def runTest(self):
        vid = test_param_get('vid', default=TEST_VID_DEFAULT)
        flow_match_test(self, config["port_map"], wildcards=ofp.OFPFW_ALL, 
                        vlan_vid=vid)

@group('smoke')
class AddVLANTag(BaseMatchCase):
    """
    Add a VLAN tag to an untagged packet
    """
    def runTest(self):
        new_vid = 2
        sup_acts = self.supported_actions
        if not(sup_acts & 1<<ofp.OFPAT_SET_VLAN_VID):
            skip_message_emit(self, "Add VLAN tag test")
            return

        len = 100
        len_w_vid = 104
        pkt = simple_tcp_packet(pktlen=len)
        exp_pkt = simple_tcp_packet(pktlen=len_w_vid, dl_vlan_enable=True, 
                                    vlan_vid=new_vid)
        vid_act = ofp.action.set_vlan_vid()
        vid_act.vlan_vid = new_vid

        flow_match_test(self, config["port_map"], pkt=pkt, 
                        exp_pkt=exp_pkt, action_list=[vid_act])

@disabled
class PacketOnly(base_tests.DataPlaneOnly):
    """
    Just send a packet thru the switch
    """

    def runTest(self):
        pkt = simple_tcp_packet()
        of_ports = config["port_map"].keys()
        of_ports.sort()
        ing_port = of_ports[0]
        logging.info("Sending packet to " + str(ing_port))
        logging.debug("Data: " + str(pkt).encode('hex'))
        self.dataplane.send(ing_port, str(pkt))

@disabled
class PacketOnlyTagged(base_tests.DataPlaneOnly):
    """
    Just send a packet thru the switch
    """

    def runTest(self):
        vid = test_param_get('vid', default=TEST_VID_DEFAULT)
        pkt = simple_tcp_packet(dl_vlan_enable=True, vlan_vid=vid)
        of_ports = config["port_map"].keys()
        of_ports.sort()
        ing_port = of_ports[0]
        logging.info("Sending packet to " + str(ing_port))
        logging.debug("Data: " + str(pkt).encode('hex'))
        self.dataplane.send(ing_port, str(pkt))

class ModifyVID(BaseMatchCase):
    """
    Modify the VLAN ID in the VLAN tag of a tagged packet
    """
    def setUp(self):
        BaseMatchCase.setUp(self)
        self.ing_port=False

    def runTest(self):
        old_vid = 2
        new_vid = 3
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_VLAN_VID):
            skip_message_emit(self, "Modify VLAN tag test")
            return

        pkt = simple_tcp_packet(dl_vlan_enable=True, vlan_vid=old_vid)
        exp_pkt = simple_tcp_packet(dl_vlan_enable=True, vlan_vid=new_vid)
        vid_act = ofp.action.set_vlan_vid()
        vid_act.vlan_vid = new_vid

        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt,
                        action_list=[vid_act], ing_port=self.ing_port)

class ModifyVIDToIngress(ModifyVID):
    """
    Modify the VLAN ID in the VLAN tag of a tagged packet and send to
    ingress port
    """
    def setUp(self):
        BaseMatchCase.setUp(self)
        self.ing_port=True

class ModifyVIDWithTagMatchWildcarded(BaseMatchCase):
    """
    With vlan ID and priority wildcarded, perform SET_VLAN_VID ofp.action.
    The same flow should match on both untagged and tagged packets.
    """
    def runTest(self):
        old_vid = 2
        new_vid = 3
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_VLAN_VID):
            skip_message_emit(self, "ModifyVIDWithTagWildcarded test")
            return

        of_ports = config["port_map"].keys()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")
        ing_port = of_ports[0]
        egress_port = of_ports[1]
        
        delete_all_flows(self.controller)

        len_untagged = 100
        len_w_vid = 104
        untagged_pkt = simple_tcp_packet(pktlen=len_untagged)
        tagged_pkt = simple_tcp_packet(pktlen=len_w_vid, 
                                       dl_vlan_enable=True, vlan_vid=old_vid)
        exp_pkt = simple_tcp_packet(pktlen=len_w_vid, dl_vlan_enable=True,
                                    vlan_vid=new_vid)
        wildcards = (required_wildcards(self) | ofp.OFPFW_DL_VLAN |
                     ofp.OFPFW_DL_VLAN_PCP)
        vid_act = ofp.action.set_vlan_vid()
        vid_act.vlan_vid = new_vid
        request = flow_msg_create(self, untagged_pkt, ing_port=ing_port, 
                                  wildcards=wildcards, egr_ports=egress_port,
                                  action_list=[vid_act])
        flow_msg_install(self, request)

        logging.debug("Send untagged packet: " + str(ing_port) + " to " + 
                        str(egress_port))
        self.dataplane.send(ing_port, str(untagged_pkt))
        verify_packets(self, exp_pkt, [egress_port])

        logging.debug("Send tagged packet: " + str(ing_port) + " to " + 
                        str(egress_port))
        self.dataplane.send(ing_port, str(tagged_pkt))
        verify_packets(self, exp_pkt, [egress_port])

class ModifyVlanPcp(BaseMatchCase):
    """
    Modify the priority field of the VLAN tag of a tagged packet
    """
    def runTest(self):
        vid          = 123
        old_vlan_pcp = 2
        new_vlan_pcp = 3
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_VLAN_PCP):
            skip_message_emit(self, "Modify VLAN priority test")
            return

        pkt = simple_tcp_packet(dl_vlan_enable=True, vlan_vid=vid, vlan_pcp=old_vlan_pcp)
        exp_pkt = simple_tcp_packet(dl_vlan_enable=True, vlan_vid=vid, vlan_pcp=new_vlan_pcp)
        vid_act = ofp.action.set_vlan_pcp()
        vid_act.vlan_pcp = new_vlan_pcp

        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt,
                        action_list=[vid_act])

class StripVLANTag(BaseMatchCase):
    """
    Strip the VLAN tag from a tagged packet
    """
    def runTest(self):
        old_vid = 2
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_STRIP_VLAN):
            skip_message_emit(self, "Strip VLAN tag test")
            return

        len_w_vid = 104
        len = 100
        pkt = simple_tcp_packet(pktlen=len_w_vid, dl_vlan_enable=True, 
                                vlan_vid=old_vid)
        exp_pkt = simple_tcp_packet(pktlen=len)
        vid_act = ofp.action.strip_vlan()

        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt,
                        action_list=[vid_act])

class StripVLANTagWithTagMatchWildcarded(BaseMatchCase):
    """
    Strip the VLAN tag from a tagged packet.
    Differs from StripVLANTag in that VID and PCP are both wildcarded.
    """
    def runTest(self):
        old_vid = 2
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_STRIP_VLAN):
            skip_message_emit(self, "StripVLANTagWithTagWildcarded test")
            return

        len_w_vid = 104
        len_untagged = 100
        pkt = simple_tcp_packet(pktlen=len_w_vid, dl_vlan_enable=True, 
                                vlan_vid=old_vid)
        exp_pkt = simple_tcp_packet(pktlen=len_untagged)
        wildcards = (required_wildcards(self) | ofp.OFPFW_DL_VLAN |
                     ofp.OFPFW_DL_VLAN_PCP)
        vid_act = ofp.action.strip_vlan()

        flow_match_test(self, config["port_map"], 
                        wildcards=wildcards,
                        pkt=pkt, exp_pkt=exp_pkt,
                        action_list=[vid_act])

def init_pkt_args():
    """
    Pass back a dictionary with default packet arguments
    """
    args = {}
    args["eth_src"] = '00:23:45:67:89:AB'

    dl_vlan_enable=False
    vlan_vid=-1
    if config["test-params"]["vid"]:
        dl_vlan_enable=True
        vlan_vid = config["test-params"]["vid"]

# Unpack operator is ** on a dictionary

    return args

class ModifyL2Src(BaseMatchCase):
    """
    Modify the source MAC address (TP1)
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_DL_SRC):
            skip_message_emit(self, "ModifyL2Src test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['eth_src'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2)

class ModifyL2Dst(BaseMatchCase):
    """
    Modify the dest MAC address (TP1)
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_DL_DST):
            skip_message_emit(self, "ModifyL2dst test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['eth_dst'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2)

class ModifyL3Src(BaseMatchCase):
    """
    Modify the source IP address of an IP packet (TP1)
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_NW_SRC):
            skip_message_emit(self, "ModifyL3Src test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['ip_src'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2)

class ModifyL3Dst(BaseMatchCase):
    """
    Modify the dest IP address of an IP packet (TP1)
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_NW_DST):
            skip_message_emit(self, "ModifyL3Dst test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['ip_dst'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2)

class ModifyL4Src(BaseMatchCase):
    """
    Modify the source TCP port of a TCP packet (TP1)
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_TP_SRC):
            skip_message_emit(self, "ModifyL4Src test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['tcp_sport'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2)

class ModifyL4SrcUdp(BaseMatchCase):
    """
    Modify the source UDP port of a UDP packet
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_TP_DST):
            skip_message_emit(self, "ModifyL4SrcUdp test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['udp_sport'],
                                                check_test_params=True, tp="udp")
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt,
                        action_list=acts, max_test=2)

class ModifyL4Dst(BaseMatchCase):
    """
    Modify the dest TCP port of a TCP packet (TP1)
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_TP_DST):
            skip_message_emit(self, "ModifyL4Dst test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['tcp_dport'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2)

class ModifyL4DstUdp(BaseMatchCase):
    """
    Modify the dest UDP port of a UDP packet
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_TP_DST):
            skip_message_emit(self, "ModifyL4DstUdp test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['udp_dport'],
                                                check_test_params=True, tp="udp")
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt,
                        action_list=acts, max_test=2)

class ModifyTOS(BaseMatchCase):
    """
    Modify the IP type of service of an IP packet (TP1)
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_NW_TOS):
            skip_message_emit(self, "ModifyTOS test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['ip_tos'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2, egr_count=-1)

class ModifyL2DstMC(BaseMatchCase):
    """
    Modify the L2 dest and send to 2 ports
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_DL_DST):
            skip_message_emit(self, "ModifyL2dstMC test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['eth_dst'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2, egr_count=-1)

class ModifyL2DstIngress(BaseMatchCase):
    """
    Modify the L2 dest and send to the ingress port
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_DL_DST):
            skip_message_emit(self, "ModifyL2dstIngress test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['eth_dst'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2, egr_count=0,
                        ing_port=True)

class ModifyL2DstIngressMC(BaseMatchCase):
    """
    Modify the L2 dest and send to the ingress port
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_DL_DST):
            skip_message_emit(self, "ModifyL2dstMC test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['eth_dst'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2, egr_count=-1,
                        ing_port=True)

class ModifyL2SrcMC(BaseMatchCase):
    """
    Modify the source MAC address (TP1) and send to multiple
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if not (sup_acts & 1 << ofp.OFPAT_SET_DL_SRC):
            skip_message_emit(self, "ModifyL2SrcMC test")
            return

        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=['eth_src'],
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2, egr_count=-1)

class ModifyL2SrcDstMC(BaseMatchCase):
    """
    Modify the L2 source and dest and send to 2 ports
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if (not (sup_acts & 1 << ofp.OFPAT_SET_DL_DST) or
                not (sup_acts & 1 << ofp.OFPAT_SET_DL_SRC)):
            skip_message_emit(self, "ModifyL2SrcDstMC test")
            return

        mod_fields = ['eth_dst', 'eth_src']
        (pkt, exp_pkt, acts) = pkt_action_setup(self, mod_fields=mod_fields,
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2, egr_count=-1)

class ModifyL2DstVIDMC(BaseMatchCase):
    """
    Modify the L2 dest and send to 2 ports
    """
    def runTest(self):
        sup_acts = self.supported_actions
        if (not (sup_acts & 1 << ofp.OFPAT_SET_DL_DST) or
                not (sup_acts & 1 << ofp.OFPAT_SET_VLAN_VID)):
            skip_message_emit(self, "ModifyL2DstVIDMC test")
            return

        mod_fields = ['eth_dst', 'vlan_vid']
        (pkt, exp_pkt, acts) = pkt_action_setup(self, 
             start_field_vals={'dl_vlan_enable':True}, mod_fields=mod_fields,
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2, egr_count=-1)

@group("smoke")
class ModifyAll(BaseMatchCase):
    """
    Modify all supported fields and output to a port
    """
    def runTest(self):
        sup_acts = self.supported_actions

        sup_map = {
            "eth_dst" : ofp.OFPAT_SET_DL_DST,
            "eth_src" : ofp.OFPAT_SET_DL_SRC,
            "dl_vlan_enable" : ofp.OFPAT_SET_VLAN_VID,
            "vlan_vid" : ofp.OFPAT_SET_VLAN_VID,
            "vlan_pcp" : ofp.OFPAT_SET_VLAN_PCP,
            "ip_src" : ofp.OFPAT_SET_NW_SRC,
            "ip_dst" : ofp.OFPAT_SET_NW_DST,
            "ip_tos" : ofp.OFPAT_SET_NW_TOS,
            "tcp_sport" : ofp.OFPAT_SET_TP_SRC,
            "tcp_dport" : ofp.OFPAT_SET_TP_DST,
        }

        mod_fields = [field for (field, bit) in sup_map.items() if (sup_acts & 1 << bit)]
        random.shuffle(mod_fields)
        start_field_vals = { "dl_vlan_enable" : True }
        mod_field_vals = { "dl_vlan_enable" : True }
        logging.info("modifying fields: %s" % repr(mod_fields))

        (pkt, exp_pkt, acts) = pkt_action_setup(self,
                                                mod_fields=mod_fields,
                                                start_field_vals=start_field_vals,
                                                mod_field_vals=mod_field_vals,
                                                check_test_params=True)
        flow_match_test(self, config["port_map"], pkt=pkt, exp_pkt=exp_pkt, 
                        action_list=acts, max_test=2)

class FlowToggle(BaseMatchCase):
    """
    Add flows to the table and modify them repeatedly

    This is done by using only "add" flow messages.  Since the check overlap
    flag is not set, the switch is supposed to modify the existing flow if
    the match already exists.

    Would probably be better to exercise more of the flow modify commands
    (add, modify, delete +/- strict).
    """
    def runTest(self):
        flow_count = test_param_get('ft_flow_count', default=20)
        iter_count = test_param_get('ft_iter_count', default=10)

        logging.info("Running flow toggle with %d flows, %d iterations" %
                       (flow_count, iter_count))
        acts = []
        acts.append(ofp.action.output())
        acts.append(ofp.action.output())
    
        of_ports = config["port_map"].keys()
        if len(of_ports) < 3:
            self.assertTrue(False, "Too few ports for test")
    
        for idx in range(2):
            acts[idx].port = of_ports[idx]
    
        flows = []
        flows.append([])
        flows.append([])
    
        wildcards = (required_wildcards(self) | ofp.OFPFW_DL_SRC |
                     ofp.OFPFW_DL_DST)
        # Create up the flows in an array
        for toggle in range(2):
            for f_idx in range(flow_count):
                pkt = simple_tcp_packet(tcp_sport=f_idx)
                msg = ofp.message.flow_add()
                match = packet_to_flow_match(self, pkt)
                match.in_port = of_ports[2]
                match.wildcards = wildcards
                msg.match = match
                msg.buffer_id = 0xffffffff
                msg.actions.append(acts[toggle])
                flows[toggle].append(msg)

        # Show two sample flows
        logging.debug(flows[0][0].show())
        logging.debug(flows[1][0].show())

        # Install the first set of flows
        for f_idx in range(flow_count):
            self.controller.message_send(flows[0][f_idx])
        do_barrier(self.controller)
    
        logging.info("Installed %d flows" % flow_count)
    
        # Repeatedly modify all the flows back and forth
        updates = 0
        # Report status about 5 times
        mod_val = (iter_count / 4) + 1
        start = time.time()
        for iter_idx in range(iter_count):
            if not iter_idx % mod_val:
                logging.info("Flow Toggle: iter %d of %d. " %
                               (iter_idx, iter_count) + 
                               "%d updates in %d secs" %
                               (updates, time.time() - start))
            for toggle in range(2):
                t_idx = 1 - toggle
                for f_idx in range(flow_count):
                    self.controller.message_send(flows[t_idx][f_idx])
                    updates += 1
                do_barrier(self.controller)

        end = time.time()
        divisor = end - start or (end - start + 1)
        logging.info("Flow toggle: %d iterations" % iter_count)
        logging.info("   %d flow mods in %d secs, %d mods/sec" %
                       (updates, end - start, updates/divisor))
            

# You can pick and choose these by commenting tests in or out
iter_classes = [
    basic.PacketIn,
    basic.PacketOut,
    DirectPacket,
    FlowToggle,
    DirectTwoPorts,
    DirectMCNonIngress,
    AllWildcardMatch,
    AllWildcardMatchTagged,
    SingleWildcardMatch,
    SingleWildcardMatchTagged,
    ExactMatch,
    ExactMatchTagged,
    SingleWildcardMatch,
    ModifyL2Src,
    ModifyL2Dst,
    ModifyL2SrcMC,
    ModifyL2DstMC,
    ModifyL2SrcDstMC
    ]

@disabled
class IterCases(BaseMatchCase):
    """
    Iterate over a bunch of test cases

    The cases come from the list above
    """

    def runTest(self):
        count = test_param_get('iter_count', default=10)
        tests_done = 0
        logging.info("Running iteration test " + str(count) + " times")
        start = time.time()
        last = start
        for idx in range(count):
            logging.info("Iteration " + str(idx + 1))
            for cls in iter_classes:
                test = cls()
                test.inheritSetup(self)
                test.runTest()
                tests_done += 1
                # Report update about every minute, between tests
                if time.time() - last > 60:
                    last = time.time()
                    logging.info(
                        "IterCases: Iter %d of %d; Ran %d tests in %d " %
                        (idx, count, tests_done, last - start) + 
                        "seconds so far")
        stats = all_stats_get(self)
        last = time.time()
        logging.info("\nIterCases ran %d tests in %d seconds." %
                       (tests_done, last - start))
        logging.info("    flows: %d. packets: %d. bytes: %d" %
                       (stats["flows"], stats["packets"], stats["bytes"]))
        logging.info("    active: %d. lookups: %d. matched %d." %
                       (stats["active"], stats["lookups"], stats["matched"]))

#@todo Need to implement tagged versions of the above tests
#
#@todo Implement a test case that strips tag 2, adds tag 3
# and modifies tag 4 to tag 5.  Then verify (in addition) that
# tag 6 does not get modified.

@disabled
class MixedVLAN(BaseMatchCase):
    """
    Test mixture of VLAN tag actions

    Strip tag 2 on port 1, send to port 2
    Add tag 3 on port 1, send to port 2
    Modify tag 4 to 5 on port 1, send to port 2
    All other traffic from port 1, send to port 3
    All traffic from port 2 sent to port 4
    Use exact matches with different packets for all mods
    Verify the following:  (port, vid)
        (port 1, vid 2) => VLAN tag stripped, out port 2
        (port 1, no tag) => tagged packet w/ vid 2 out port 2
        (port 1, vid 4) => tagged packet w/ vid 5 out port 2
        (port 1, vid 5) => tagged packet w/ vid 5 out port 2
        (port 1, vid 6) => tagged packet w/ vid 6 out port 2
        (port 2, no tag) => untagged packet out port 4
        (port 2, vid 2-6) => unmodified packet out port 4

    Variation:  Might try sending VID 5 to port 3 and check.
    If only VID 5 distinguishes pkt, this will fail on some platforms
    """   

@group('smoke')
class MatchEach(base_tests.SimpleDataPlane):
    """
    Check that each match field is actually matched on.
    Installs two flows that differ in one field. The flow that should not
    match has a higher priority, so if that field is ignored during matching
    the packet will be sent out the wrong port.

    TODO test UDP, ARP, ICMP, etc.
    """
    def runTest(self):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        delete_all_flows(self.controller)

        pkt = simple_tcp_packet(dl_vlan_enable=True, vlan_vid=2)
        ingress_port = of_ports[0]
        egress_port = of_ports[1]

        def testField(field, mask):
            logging.info("Testing field %s" % field)

            def addFlow(matching, priority, output_port):
                match = packet_to_flow_match(self, pkt)
                self.assertTrue(match is not None, "Could not generate flow match from pkt")
                match.wildcards &= ~ofp.OFPFW_IN_PORT
                match.in_port = ingress_port
                if not matching:
                    # Make sure flow doesn't match
                    orig = getattr(match, field)
                    if isinstance(orig, list):
                        new = map(lambda a: ~a[0] & a[1], zip(orig, mask))
                    else:
                        new = ~orig & mask
                    setattr(match, field, new)
                request = ofp.message.flow_add()
                request.match = match
                request.buffer_id = 0xffffffff
                request.priority = priority
                act = ofp.action.output()
                act.port = output_port
                request.actions.append(act)
                logging.info("Inserting flow")
                self.controller.message_send(request)

            # This flow should match.
            addFlow(matching=True, priority=0, output_port=egress_port)
            # This flow should not match, but it has a higher priority.
            addFlow(matching=False, priority=1, output_port=ofp.OFPP_IN_PORT)

            do_barrier(self.controller)

            logging.info("Sending packet to dp port " + str(ingress_port))
            self.dataplane.send(ingress_port, str(pkt))

            exp_pkt_arg = None
            exp_port = None
            if config["relax"]:
                exp_pkt_arg = pkt
                exp_port = egress_port

            (rcv_port, rcv_pkt, pkt_time) = self.dataplane.poll(port_number=exp_port,
                                                                exp_pkt=exp_pkt_arg)
            self.assertTrue(rcv_pkt is not None, "Did not receive packet")
            logging.debug("Packet len " + str(len(rcv_pkt)) + " in on " + str(rcv_port))
            self.assertEqual(rcv_port, egress_port, "Unexpected receive port")
            self.assertEqual(str(pkt), str(rcv_pkt), 'Response packet does not match send packet')

        wildcards = required_wildcards(self)
        # TODO in_port
        if not (wildcards & ofp.OFPFW_DL_SRC):
            testField("eth_src", [0xff]*6)
        if not (wildcards & ofp.OFPFW_DL_DST):
            testField("eth_dst", [0xff]*6)
        if not (wildcards & ofp.OFPFW_DL_TYPE):
            testField("eth_type", 0xffff)
        if not (wildcards & ofp.OFPFW_DL_VLAN):
            testField("vlan_vid", 0xfff)
        # TODO vlan_pcp
        if not (wildcards & ofp.OFPFW_NW_SRC_ALL):
            testField("ipv4_src", 0xffffffff)
        if not (wildcards & ofp.OFPFW_NW_DST_ALL):
            testField("ipv4_dst", 0xffffffff)
        if not (wildcards & ofp.OFPFW_NW_TOS):
            testField("ip_dscp", 0x3f)
        if not (wildcards & ofp.OFPFW_NW_PROTO):
            testField("ip_proto", 0xff)
        if not (wildcards & ofp.OFPFW_TP_SRC):
            testField("tcp_src", 0xffff)
        if not (wildcards & ofp.OFPFW_TP_DST):
            testField("tcp_dst", 0xffff)

class DirectBadPacketBase(base_tests.SimpleDataPlane):
    """
    Base class for sending single packets with single flow table entries.
    Used to verify matching of unusual packets and parsing/matching of 
    corrupted packets.

    The idea is to generate packets that may either be totally malformed or 
    malformed just enough to trick the flow matcher into making mistakes.

    Generate a 'bad' packet
    Generate and install a matching flow
    Add action to direct the packet to an egress port
    Send the packet to ingress dataplane port
    Verify the packet is received at the egress port only
    """

    RESULT_MATCH = "MATCH"
    RESULT_NOMATCH = "NO MATCH"
    RESULT_ANY = "ANY MATCH"
    
    def runTest(self):
        pass
        # TODO:
        # - ICMP?
        # - VLAN?
        # - action

    def createMatch(self, **kwargs):
        match = ofp.match()
        match.wildcards = ofp.OFPFW_ALL
        fields = {
            'eth_dst': ofp.OFPFW_DL_DST,
            'eth_src': ofp.OFPFW_DL_SRC,
            'eth_type': ofp.OFPFW_DL_TYPE,
            'vlan_vid': ofp.OFPFW_DL_VLAN,
            'ipv4_src': ofp.OFPFW_NW_SRC_MASK,
            'ipv4_dst': ofp.OFPFW_NW_DST_MASK,
            'ip_dscp': ofp.OFPFW_NW_TOS,
            'ip_proto': ofp.OFPFW_NW_PROTO,
            'tcp_src': ofp.OFPFW_TP_SRC,
            'tcp_dst': ofp.OFPFW_TP_DST,
        }
        for key in kwargs:
            setattr(match, key, kwargs[key])
            match.wildcards &= ~fields[key]
        return match

    def testPktsAgainstFlow(self, pkts, acts, match):
        if type(acts) != list:
            acts = [acts]
        for info in pkts:
            title, pkt, expected_result = info
            self.testPktAgainstFlow(title, pkt, acts, match, expected_result)

    def testPktAgainstFlow(self, title, pkt, acts, match, expected_result):
        of_ports = config["port_map"].keys()
        of_ports.sort()
        self.assertTrue(len(of_ports) > 1, "Not enough ports for test")

        delete_all_flows(self.controller)

        ingress_port = of_ports[0]
        egress_port = of_ports[1]
        
        logging.info("Testing packet '%s', expect result %s" % 
                       (title, expected_result))
        logging.info("Ingress %s to egress %s" % 
                       (str(ingress_port), str(egress_port)))
        logging.info("Packet:")
        logging.info(inspect_packet(pkt))

        match.in_port = ingress_port

        request = ofp.message.flow_add()
        request.match = match
        request.priority = 1

        request.buffer_id = 0xffffffff
        for act in acts:
            act.port = egress_port
            request.actions.append(act)

        logging.info("Inserting flow")
        self.controller.message_send(request)

        # This flow speeds up negative tests
        logging.info("Inserting catch-all flow")
        request2 = ofp.message.flow_add()
        request2.match = self.createMatch()
        request2.match.wildcards &= ~ofp.OFPFW_IN_PORT
        request2.match.in_port = ingress_port

        request2.priority = 0
        act = ofp.action.output()
        act.port = ofp.OFPP_IN_PORT
        request2.actions.append(act)
        self.controller.message_send(request2)

        do_barrier(self.controller)

        pkt_str = str(pkt)
        if config["minsize"] > len(str(pkt)):
            pkt_str += '0' * (config["minsize"] - len(str(pkt)))

        logging.info("Sending packet to dp port " + 
                       str(ingress_port))
        self.dataplane.send(ingress_port, pkt_str)

        exp_pkt_arg = None
        exp_port = None
        if config["relax"]:
            exp_pkt_arg = pkt
            exp_port = egress_port

        if expected_result == self.RESULT_MATCH:
            timeout = -1 # default timeout
        else:
            timeout = 1 # short timeout for negative tests

        (rcv_port, rcv_pkt, pkt_time) = self.dataplane.poll(exp_pkt=exp_pkt_arg,
                                                            timeout=timeout)
        if rcv_port == ingress_port:
            logging.debug("Packet matched catch-all flow")
            rcv_pkt = None

        if expected_result == self.RESULT_MATCH:
            self.assertTrue(rcv_pkt is not None, 
                            "Did not receive packet, expected a match")
            logging.debug("Packet len " + str(len(rcv_pkt)) + " in on " + 
                          str(rcv_port))
            self.assertEqual(rcv_port, egress_port, "Unexpected receive port")
            str_pkt = str(pkt)
            str_rcv_pkt = str(rcv_pkt)
            str_rcv_pkt = str_rcv_pkt[0:len(str_pkt)]
            if str_pkt != str_rcv_pkt:
                logging.error("Response packet does not match send packet")
                logging.info("Response:")
                logging.info(inspect_packet(scapy.Ether(rcv_pkt)))
            self.assertEqual(str_pkt, str_rcv_pkt,
                             'Response packet does not match send packet')
        elif expected_result == self.RESULT_NOMATCH:
            self.assertTrue(rcv_pkt is None, "Received packet, expected drop")
        else:
            logging.debug("Match or drop accepted. Result = %s" %
                            ("match" if rcv_pkt is not None else "drop"))


class DirectBadIpTcpPacketsBase(DirectBadPacketBase):
    """
    Base class for TCP and UDP parsing/matching verification under corruptions
    """
    def runTest(self):
        pass

    def runTestWithProto(self, protoName = 'TCP'):
        eth_dst='00:01:02:03:04:05'
        eth_src='00:06:07:08:09:0a'
        ip_src='192.168.0.1'
        ip_dst='192.168.0.2'
        ip_tos=0
        tcp_sport=1234
        tcp_dport=80
        
        # Generate a proper packet for constructing a match
        tp = None
        if protoName == 'TCP':
            tp = scapy.TCP
            proto = 6
        elif protoName == 'UDP':
            tp = scapy.UDP
            proto = 17
        else:
            raise Exception("Passed in unknown proto name")

        match_pkt = scapy.Ether(dst=eth_dst, src=eth_src)/ \
            scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos)/ \
            tp(sport=tcp_sport, dport=tcp_dport)
        match = packet_to_flow_match(self, match_pkt)
        self.assertTrue(match is not None, 
                        "Could not generate flow match from pkt")
        match.wildcards &= ~ofp.OFPFW_IN_PORT
        
        def testPacket(title, pkt, result):
            act = ofp.action.output()
            pkts = [
                [title, pkt, result]
            ]
            self.testPktsAgainstFlow(pkts, act, match)
        
        # Try incomplete IP headers
        testPacket("Incomplete IP header (1 bytes)",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                str(scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto))[0:1],
            self.RESULT_NOMATCH,
        )
        testPacket("Incomplete IP header (2 bytes)",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                str(scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto))[0:2],
            self.RESULT_NOMATCH,
        )
        testPacket("Incomplete IP header (3 bytes)",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                str(scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto))[0:3],
            self.RESULT_NOMATCH,
        )
        testPacket("Incomplete IP header (12 bytes)",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                str(scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto))[0:12],
            self.RESULT_NOMATCH,
        )
        testPacket("Incomplete IP header (16 bytes)",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                str(scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto))[0:16],
            self.RESULT_NOMATCH,
        )
        testPacket("Incomplete IP header (19 bytes)",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                str(scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto))[0:19],
            self.RESULT_NOMATCH,
        )
            
        # Try variations where the TCP header is missing or incomplete. As we 
        # saw bugs before where buffers were reused and lengths weren't honored,
        # we initiatlize once with a non-matching full packet and once with a 
        # matching full packet.
        testPacket("Non-Matching TCP packet, warming buffer",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto)/ \
                tp(sport=tcp_sport, dport=tcp_dport + 1),
            self.RESULT_NOMATCH,
        )
        testPacket("Missing TCP header, buffer warmed with non-match",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto),
            self.RESULT_NOMATCH,
        )
        testPacket("Matching TCP packet, warming buffer",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto)/ \
                tp(sport=tcp_sport, dport=tcp_dport),
            self.RESULT_MATCH,
        )
        testPacket("Missing TCP header, buffer warmed with match",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto),
            self.RESULT_NOMATCH,
        )
        testPacket("Truncated TCP header: 2 bytes",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto)/ \
                (str(tp(sport=tcp_sport, dport=tcp_dport))[0:2]),
            self.RESULT_NOMATCH,
        )
            
        # Play with IP header length values that put the start of TCP either
        # inside the generated TCP header or beyond. In some cases it may even
        # be beyond the packet boundary. Also play with IP options and more 
        # importantly IP total length corruptions.
        testPacket("TCP packet, corrupt ihl (0x6)",
            simple_tcp_packet(ip_ihl=6),
            self.RESULT_NOMATCH,
        )
        testPacket("TCP packet, corrupt ihl (0xf)",
            simple_tcp_packet(ip_ihl=0xf), # ihl = 15 * 4 = 60
            self.RESULT_NOMATCH,
        )
        testPacket("TCP packet, corrupt ihl and total length",
            simple_tcp_packet(ip_ihl=0xf, pktlen=56), # ihl = 15 * 4 = 60,
            self.RESULT_NOMATCH,
        )
        testPacket("Corrupt IPoption: First 4 bytes of matching TCP header",
            simple_tcp_packet(
                ip_options=scapy.IPOption('\x04\xd2\x00\x50'), 
                tcp_dport=2, tcp_sport=2
            ),
            self.RESULT_NOMATCH,
        )
        testPacket("Missing TCP header, corrupt ihl",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, ihl=0xf, proto=proto),
            self.RESULT_NOMATCH,
        )
        testPacket("Missing TCP header, corrupt total length",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto, len= 100),
            self.RESULT_NOMATCH,
        )
        testPacket("Missing TCP header, corrupt ihl and total length",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, ihl=0xf, proto=proto, len=43),
            self.RESULT_NOMATCH,
        )
        testPacket("Incomplete IP header (12 bytes), corrupt ihl and total length",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                str(scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto, ihl=10, len=43))[0:12],
            self.RESULT_NOMATCH,
        )
        testPacket("Incomplete IP header (16 bytes), corrupt ihl and total length",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                str(scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto, ihl=10, len=43))[0:16],
            self.RESULT_NOMATCH,
        )
            
        # Try an incomplete TCP header that has enough bytes to carry source and
        # destination ports. As that is all we care about during matching, some
        # implementations may match and some may drop the packet
        testPacket("Incomplete TCP header: src/dst port present",
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=proto)/ \
                (str(tp(sport=tcp_sport, dport=tcp_dport))[0:4]),
            self.RESULT_ANY,
        )

        for i in range(1):
            for length in range(40 / 4): # IPv4 options are a maximum of 40 in length
                bytes = "".join([("%c" % random.randint(0, 255)) for x in range(length * 4)])
                eth = scapy.Ether(dst=eth_dst, src=eth_src)
                ip = scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, ihl=5 + length, proto=proto)
                tcp = tp(sport=tcp_sport, dport=tcp_dport+1)
                pkt = eth / ip
                pkt = pkt / bytes
                pkt = pkt / str(tcp)
                testPacket("Random IP options len = %d - TP match must fail" % length * 4, 
                    pkt, 
                    self.RESULT_NOMATCH
                )

                eth = scapy.Ether(dst=eth_dst, src=eth_src)
                ip = scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, ihl=5 + length, proto=proto)
                tcp = tp(sport=tcp_sport, dport=tcp_dport)
                pkt = eth / ip
                pkt = pkt / bytes
                pkt = pkt / str(tcp)

                testPacket("Random IP options len = %d - May match", 
                    pkt, 
                    self.RESULT_ANY
                )
        

class DirectBadIpTcpPackets(DirectBadIpTcpPacketsBase):
    """
    Verify IP/TCP parsing and matching. Focus on packet corruptions 
    """
    def runTest(self):
        self.runTestWithProto(protoName = 'TCP')

class DirectBadIpUdpPackets(DirectBadIpTcpPacketsBase):
    """
    Verify IP/UDP parsing and matching. Focus on packet corruptions 
    """
    def runTest(self):
        self.runTestWithProto(protoName = 'UDP')

class DirectBadLlcPackets(DirectBadPacketBase):
    """
    Verify LLC/SNAP parsing and matching. Focus on packet corruptions 
    """
    def runTest(self):
        eth_dst='00:01:02:03:04:05'
        eth_src='00:06:07:08:09:0a'
        ip_src='192.168.0.1'
        ip_dst='192.168.0.2'
        ip_tos=0
        tcp_sport=1234
        tcp_dport=80

        IS_SNAP_IP = 1
        IS_SNAP_IP_CORRUPT = 2
        IS_NOT_SNAP_IP = 3

        def testPacketTcpMatch(title, llc):
            match_pkt = scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos)/ \
                scapy.TCP(sport=tcp_sport, dport=tcp_dport)
            match = packet_to_flow_match(self, match_pkt)
            self.assertTrue(match is not None, 
                            "Could not generate flow match from pkt")
            match.wildcards &= ~ofp.OFPFW_IN_PORT
            act = ofp.action.output()
            
            self.testPktsAgainstFlow(
                [[
                    "TCP match - LLC frame correct length - %s" % title,
                    scapy.Ether(dst=eth_dst, src=eth_src, type=len(llc)) / llc,
                    self.RESULT_ANY,
                ]],
                act, match
            )
    
            # Corrupt length field
            ethLen = random.randint(0, 1535)
            self.testPktsAgainstFlow(
                [[
                    "TCP match - LLC frame corrupted length - %s" % title,
                    scapy.Ether(dst=eth_dst, src=eth_src, type=ethLen) / llc,
                    self.RESULT_ANY,
                ]],
                act, match
            )

        def testPacketEthSrcDstMatch(title, llc):
            # Matching based on Ethernet source and destination
            match_pkt = scapy.Ether(dst=eth_dst, src=eth_src)
            match = packet_to_flow_match(self, match_pkt)
            self.assertTrue(match is not None, 
                            "Could not generate flow match from pkt")
            match.wildcards &= ~ofp.OFPFW_IN_PORT
            match.wildcards |= ofp.OFPFW_DL_TYPE
            self.testPktsAgainstFlow(
                [[
                    "Eth addr match - LLC frame correct length- %s" % title,
                    scapy.Ether(dst=eth_dst, src=eth_src, type=len(llc)) / llc,
                    self.RESULT_MATCH,
                ]],
                ofp.action.output(), match
            )
    
            # Corrupt length field
            ethLen = random.randint(0, 1535)
            self.testPktsAgainstFlow(
                [[
                    "Eth addr match - LLC frame corrupted length- %s" % title,
                    scapy.Ether(dst=eth_dst, src=eth_src, type=ethLen) / llc,
                    self.RESULT_ANY,
                ]],
                ofp.action.output(), match
            )
            
        def testPacketEthSrcDstTypeMatch(title, llc, is_snap_ip):
            # Matching based on Ethernet source, destination and type
            match_pkt = scapy.Ether(dst=eth_dst, src=eth_src, type=0x800)
            match = packet_to_flow_match(self, match_pkt)
            self.assertTrue(match is not None, 
                            "Could not generate flow match from pkt")
            match.wildcards &= ~ofp.OFPFW_IN_PORT
            if is_snap_ip == IS_SNAP_IP:
                is_match = self.RESULT_MATCH
            elif is_snap_ip == IS_SNAP_IP_CORRUPT:
                is_match = self.RESULT_ANY
            else:
                is_match = self.RESULT_NOMATCH
            self.testPktsAgainstFlow(
                [[
                    "Eth addr+type match - LLC frame correct length - %s" % title,
                    scapy.Ether(dst=eth_dst, src=eth_src, type=len(llc)) / llc,
                    is_match,
                ]],
                ofp.action.output(), match
            )
    
            # Corrupt length field
            ethLen = random.randint(0, 1535)
            self.testPktsAgainstFlow(
                [[
                    "Eth addr+type match - LLC frame corrupted length - %s" % title,
                    scapy.Ether(dst=eth_dst, src=eth_src, type=ethLen) / llc,
                    self.RESULT_ANY,
                ]],
                ofp.action.output(), match
            )

        def testPacket(title, llc, is_snap_ip):
            testPacketTcpMatch(title, llc)
            testPacketEthSrcDstMatch(title, llc)
            testPacketEthSrcDstTypeMatch(title, llc, is_snap_ip)

        testPacket("LLC - No SNAP - No Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x03),
            IS_NOT_SNAP_IP,
        )
        testPacket("LLC - No SNAP - Small Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x03) / ("S" * 10),
            IS_NOT_SNAP_IP,
        )
        testPacket("LLC - No SNAP - Max -1 Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x03) / ("S" * (1500 - 3 - 1)),
            IS_NOT_SNAP_IP,
        )
        testPacket("LLC - No SNAP - Max Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x03) / ("S" * (1500 - 3)),
            IS_NOT_SNAP_IP,
        )
        testPacket("LLC - SNAP - Small bogus payload",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000000, code=0x800) / ("S" * 10),
            IS_SNAP_IP_CORRUPT,
        )
        testPacket("LLC - SNAP - Max -1 bogus payload",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000000, code=0x3) / ("S" * (1500 - 3 - 5 - 1)),
            IS_NOT_SNAP_IP,
        )
        testPacket("LLC - SNAP - Max bogus payload",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000000, code=0x3) / ("S" * (1500 - 3 - 5)),
            IS_NOT_SNAP_IP,
        )
        testPacket("LLC - SNAP - IP - TCP",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000000, code=0x800)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=6)/ \
                scapy.TCP(sport=tcp_sport, dport=tcp_dport),
            IS_SNAP_IP,
        )
        

class DirectLlcPackets(DirectBadPacketBase):
    """
    Verify LLC/SNAP parsing (valid and corrupted packets) and matching
    """
    def runTest(self):
        eth_dst='00:01:02:03:04:05'
        eth_src='00:06:07:08:09:0a'
        ip_src='192.168.0.1'
        ip_dst='192.168.0.2'
        ip_tos=0
        tcp_sport=1234
        tcp_dport=80

        # Test ethertype in face of LLC/SNAP and OFP_DL_TYPE_NOT_ETH_TYPE
        IS_SNAP_NOT_IP = 1
        IS_SNAP_AND_IP = 2
        IS_NOT_SNAP = 3

        def testPacketEthTypeIP(title, llc, is_snap):
            match_pkt = scapy.Ether(dst=eth_dst, src=eth_src, type=0x800)
            match = packet_to_flow_match(self, match_pkt)
            self.assertTrue(match is not None, 
                            "Could not generate flow match from pkt")
            match.wildcards &= ~ofp.OFPFW_IN_PORT
            pkts = []
            if is_snap == IS_NOT_SNAP or is_snap == IS_SNAP_NOT_IP:
                result = self.RESULT_NOMATCH
            else:
                result = self.RESULT_MATCH
            pkts.append([
                "Ether type 0x800 match - %s" % title,
                scapy.Ether(dst=eth_dst, src=eth_src, type=len(llc)) / llc,
                result,
            ])
            act = ofp.action.output()
            self.testPktsAgainstFlow(pkts, act, match)
    
        def testPacketEthTypeNotEth(title, llc, is_snap):
            match_pkt = scapy.Ether(dst = eth_dst, src = eth_src, 
                                    type = ofp.OFP_DL_TYPE_NOT_ETH_TYPE)
            match = packet_to_flow_match(self, match_pkt)
            self.assertTrue(match is not None, 
                            "Could not generate flow match from pkt")
            match.wildcards &= ~ofp.OFPFW_IN_PORT
            pkts = []
            if is_snap == IS_NOT_SNAP:
                result = self.RESULT_MATCH
            else:
                result = self.RESULT_NOMATCH
            pkts.append([
                "Ether type OFP_DL_TYPE_NOT_ETH_TYPE match - %s" % title,
                scapy.Ether(dst=eth_dst, src=eth_src, type=len(llc)) / llc,
                result,
            ])
            act = ofp.action.output()
            self.testPktsAgainstFlow(pkts, act, match)
    
        def testPacket(title, llc, is_snap):
            testPacketEthTypeIP(title, llc, is_snap)
            testPacketEthTypeNotEth(title, llc, is_snap)
        
        testPacket("LLC - No SNAP - No Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x03),
            IS_NOT_SNAP,
        )
        testPacket("LLC (with information field) - No SNAP - No Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x12) / "S",
            IS_NOT_SNAP,
        )
        testPacket("LLC - No SNAP - Small Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x03) / ("S" * 10),
            IS_NOT_SNAP,
        )
        testPacket("LLC - No SNAP - Max -1 Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x03) / ("S" * (1500 - 3 - 1)),
            IS_NOT_SNAP,
        )
        testPacket("LLC - No SNAP - Max Payload",
            scapy.LLC(dsap=0x33, ssap=0x44, ctrl=0x03) / ("S" * (1500 - 3)),
            IS_NOT_SNAP,
        )
        testPacket("LLC - SNAP - Non-default OUI",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000001, code=0x800) / ("S" * 10),
            IS_NOT_SNAP,
        )
        testPacket("LLC - SNAP - Default OUI",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000000, code=0x800) / ("S" * 10),
            IS_SNAP_AND_IP,
        )
        testPacket("LLC - SNAP - Max -1 bogus payload",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000000, code=0x3) / ("S" * (1500 - 3 - 5 - 1)),
            IS_SNAP_NOT_IP,
        )
        testPacket("LLC - SNAP - Max bogus payload",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000000, code=0x3) / ("S" * (1500 - 3 - 5)),
            IS_SNAP_NOT_IP,
        )
        testPacket("LLC - SNAP - IP - TCP",
            scapy.LLC(dsap=0xaa, ssap=0xaa, ctrl=0x03)/ \
                scapy.SNAP(OUI=0x000000, code=0x800)/ \
                scapy.IP(src=ip_src, dst=ip_dst, tos=ip_tos, proto=6)/ \
                scapy.TCP(sport=tcp_sport, dport=tcp_dport),
            IS_SNAP_AND_IP,
        )


class DirectArpPackets(DirectBadPacketBase):
    """
    Verify ARP parsing (valid and corrupted packets) and ARP matching
    """
    def runTest(self):
        self.testArpHandling()

    def testArpHandling(self):
        eth_dst='00:01:02:03:04:05'
        eth_src='00:06:07:08:09:0a'
        ip_src='192.168.0.1'
        ip_dst='192.168.0.2'
        ip_src2='192.168.1.1'
        ip_dst2='192.168.1.2'
        ip_tos=0
        tcp_sport=1234
        tcp_dport=80

        def testPacket(title, arp_match, arp_pkt, result):
            pkts = []
    
            match_pkt = scapy.Ether(dst=eth_dst, src=eth_src) / arp_match
            match = packet_to_flow_match(self, match_pkt)
            self.assertTrue(match is not None, 
                            "Could not generate flow match from pkt")
            match.wildcards &= ~ofp.OFPFW_IN_PORT
            
            pkts.append([
                title,
                scapy.Ether(dst=eth_dst, src=eth_src) / arp_pkt,
                result,
            ])
    
            act = ofp.action.output()
            self.testPktsAgainstFlow(pkts, act, match)
            
        testPacket("Basic ARP",
            scapy.ARP(psrc=ip_src, pdst=ip_dst, op = 1),
            scapy.ARP(hwdst = '00:00:00:00:00:00', hwsrc = eth_src,
                      psrc = ip_src, pdst = ip_dst, hwlen = 6, plen = 4,
                      ptype = 0x800, hwtype = 1, op = 1),
            self.RESULT_MATCH
        )
        # More stuff:
        # - Non matches on any property
        # - Corrupted hwlen and plen
        # - Other hwtype, ptype
        # - Truncated ARP pkt

    
class DirectVlanPackets(DirectBadPacketBase):
    """
    Verify VLAN parsing (valid and corrupted packets) and ARP matching
    """
    def runTest(self):
        eth_dst='00:01:02:03:04:05'
        eth_src='00:06:07:08:09:0a'
        ip_src='192.168.0.1'
        ip_dst='192.168.0.2'
        ip_src2='192.168.1.1'
        ip_dst2='192.168.1.2'
        ip_tos=0
        tcp_sport=1234
        tcp_dport=80

        def testPacket(title, match, pkt, result):
            pkts = []
    
            self.assertTrue(match is not None, 
                            "Could not generate flow match from pkt")
            match.wildcards &= ~ofp.OFPFW_IN_PORT
            
            pkts.append([
                "%s" % title,
                pkt,
                result,
            ])
    
            act = ofp.action.output()
            self.testPktsAgainstFlow(pkts, act, match)

        testPacket("Basic MAC matching - IPv4 payload",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src)),
            scapy.Ether(dst=eth_dst, src=eth_src, type=0x800) / scapy.IP(),
            self.RESULT_MATCH
        )
        testPacket("Basic MAC matching - VMware beacon - no payload",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src)),
            scapy.Ether(dst=eth_dst, src=eth_src, type=0x8922),
            self.RESULT_MATCH
        )
        testPacket("Basic MAC matching - VMware beacon - with payload",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src)),
            scapy.Ether(dst=eth_dst, src=eth_src, type=0x8922)/ ("X" * 1),
            self.RESULT_MATCH
        )
        testPacket("Basic MAC matching - IPv6 payload",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src)),
            scapy.Ether(dst=eth_dst, src=eth_src) / scapy.IPv6(),
            self.RESULT_MATCH
        )
        testPacket("Basic MAC matching with VLAN tag present",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src)),
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.Dot1Q(prio=5, vlan=1000)/ \
                scapy.IP(),
            self.RESULT_MATCH
        )
        testPacket("Basic MAC matching with VLAN tag present",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src),
                             eth_type=0x800),
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.Dot1Q(prio=5, vlan=1000)/ \
                scapy.IP(),
            self.RESULT_MATCH
        )
        testPacket("Ether matching with VLAN tag present - No type match",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src),
                             eth_type=0x801),
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.Dot1Q(prio=5, vlan=1000)/ \
                scapy.IP(),
            self.RESULT_NOMATCH
        )
        testPacket("Ether matching with VLAN tag present - No type match 0x8100",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src),
                             eth_type=0x8100),
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.Dot1Q(prio=5, vlan=1000)/ \
                scapy.IP(),
            self.RESULT_NOMATCH
        )
        testPacket("IP matching - VLAN tag",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src),
                             eth_type=0x0800,
                             ipv4_src=parse_ip(ip_src), ipv4_dst=parse_ip(ip_dst)),
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.Dot1Q(prio=5, vlan=1000)/ \
                scapy.IP(src=ip_src, dst=ip_dst),
            self.RESULT_MATCH
        )
        # XXX:
        # - Matching on VLAN ID and Prio
        # - Actions

@nonstandard
class DirectVlanPacketsDoubleTagged(DirectVlanPackets):
    """
    VLAN parsing for double tagged packets.  Spec is ambiguous about
    the treatment of these cases, so broken out to be non-standard
    """
    def runTest(self):
        eth_dst='00:01:02:03:04:05'
        eth_src='00:06:07:08:09:0a'
        ip_src='192.168.0.1'
        ip_dst='192.168.0.2'
        ip_src2='192.168.1.1'
        ip_dst2='192.168.1.2'
        ip_tos=0
        tcp_sport=1234
        tcp_dport=80

        def testPacket(title, match, pkt, result):
            pkts = []
    
            self.assertTrue(match is not None, 
                            "Could not generate flow match from pkt")
            match.wildcards &= ~ofp.OFPFW_IN_PORT
            
            pkts.append([
                "%s" % title,
                pkt,
                result,
            ])
    
            act = ofp.action.output()
            self.testPktsAgainstFlow(pkts, act, match)
        testPacket("Ether matching with double VLAN tag - Wrong type match",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src),
                             eth_type=0x800),
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.Dot1Q(prio=5, vlan=1000)/ \
                scapy.Dot1Q(prio=3, vlan=1005)/ \
                scapy.IP(),
            self.RESULT_NOMATCH
        )
        testPacket("Ether matching with double VLAN tag - Type match",
            self.createMatch(eth_dst=parse_mac(eth_dst), eth_src=parse_mac(eth_src),
                             eth_type=0x8100),
            scapy.Ether(dst=eth_dst, src=eth_src)/ \
                scapy.Dot1Q(prio=5, vlan=1000)/ \
                scapy.Dot1Q(prio=3, vlan=1005)/ \
                scapy.IP(),
            self.RESULT_MATCH
        )

    

if __name__ == "__main__":
    print "Please run through oft script:  ./oft --test_spec=basic"
