diff options
Diffstat (limited to 'core')
-rw-r--r-- | core/__init__.py | 1 | ||||
-rw-r--r-- | core/component_factory.py | 20 | ||||
-rw-r--r-- | core/loader/loader_servant.py | 6 | ||||
-rw-r--r-- | core/vnf_controller.py | 59 | ||||
-rw-r--r-- | core/vnf_controller_p2p.py | 64 | ||||
-rw-r--r-- | core/vnf_controller_pvp.py | 69 | ||||
-rw-r--r-- | core/vswitch_controller_p2p.py | 28 | ||||
-rw-r--r-- | core/vswitch_controller_pvp.py | 25 | ||||
-rw-r--r-- | core/vswitch_controller_pvvp.py | 114 |
9 files changed, 197 insertions, 189 deletions
diff --git a/core/__init__.py b/core/__init__.py index 0b41aaca..e39ec88e 100644 --- a/core/__init__.py +++ b/core/__init__.py @@ -16,5 +16,4 @@ """ import core.component_factory from core.traffic_controller import (ITrafficController) -from core.vnf_controller import (IVnfController) from core.vswitch_controller import (IVswitchController) diff --git a/core/component_factory.py b/core/component_factory.py index e8bb4de3..4da37fb7 100644 --- a/core/component_factory.py +++ b/core/component_factory.py @@ -18,8 +18,8 @@ from core.traffic_controller_rfc2544 import TrafficControllerRFC2544 from core.vswitch_controller_p2p import VswitchControllerP2P from core.vswitch_controller_pvp import VswitchControllerPVP -from core.vnf_controller_p2p import VnfControllerP2P -from core.vnf_controller_pvp import VnfControllerPVP +from core.vswitch_controller_pvvp import VswitchControllerPVVP +from core.vnf_controller import VnfController from tools.load_gen.stress.stress import Stress from tools.load_gen.stress_ng.stress_ng import StressNg from tools.load_gen.dummy.dummy import DummyLoadGen @@ -58,16 +58,16 @@ def create_vswitch(deployment_scenario, vswitch_class, bidir=True): :param vswitch_class: Reference to vSwitch class to be used. :return: IVSwitchController for the deployment_scenario """ - #TODO - full mapping from all deployment_scenarios to - #correct controller class deployment_scenario = deployment_scenario.lower() if deployment_scenario.find("p2p") >= 0: return VswitchControllerP2P(vswitch_class) elif deployment_scenario.find("pvp") >= 0: return VswitchControllerPVP(vswitch_class, bidir) + elif deployment_scenario.find("pvvp") >= 0: + return VswitchControllerPVVP(vswitch_class, bidir) def create_vnf(deployment_scenario, vnf_class): - """Return a new IVnfController for the deployment_scenario. + """Return a new VnfController for the deployment_scenario. The returned controller is configured with the given VNF class. @@ -75,15 +75,9 @@ def create_vnf(deployment_scenario, vnf_class): :param deployment_scenario: The deployment scenario name :param vswitch_class: Reference to vSwitch class to be used. - :return: IVnfController for the deployment_scenario + :return: VnfController for the deployment_scenario """ - #TODO - full mapping from all deployment_scenarios to - #correct controller class - deployment_scenario = deployment_scenario.lower() - if deployment_scenario.find("p2p") >= 0: - return VnfControllerP2P(None) - elif deployment_scenario.find("pvp") >= 0: - return VnfControllerPVP(vnf_class) + return VnfController(deployment_scenario, vnf_class) def create_collector(collector_class, result_dir, test_name): """Return a new Collector of the given class diff --git a/core/loader/loader_servant.py b/core/loader/loader_servant.py index 7966532c..3b729c23 100644 --- a/core/loader/loader_servant.py +++ b/core/loader/loader_servant.py @@ -138,10 +138,12 @@ class LoaderServant(object): result = {} for _, mod in LoaderServant._load_all_modules(path): - # find all system metric loggers defined in the module + # find all classes derived from given interface, but suppress + # interface itself and any abstract class starting with iface name gens = dict((k, v) for (k, v) in list(mod.__dict__.items()) if type(v) == type and - issubclass(v, interface) and k != interface.__name__) + issubclass(v, interface) and + not k.startswith(interface.__name__)) if gens: for (genname, gen) in list(gens.items()): result[genname] = gen diff --git a/core/vnf_controller.py b/core/vnf_controller.py index be1c7c4a..3d3be040 100644 --- a/core/vnf_controller.py +++ b/core/vnf_controller.py @@ -14,35 +14,66 @@ """ VNF Controller interface """ -class IVnfController(object): - """Abstract class which defines a VNF controller +import logging - Used to set-up and control a VNF provider for a particular - deployment scenario. +class VnfController(object): + """VNF controller class + + Used to set-up and control VNFs for specified scenario + + Attributes: + _vnf_class: A class object representing the VNF to be used. + _deployment_scenario: A string describing the scenario to set-up in the + constructor. + _vnfs: A list of vnfs controlled by the controller. """ + def __init__(self, deployment_scenario, vnf_class): + """Sets up the VNF infrastructure for the PVP deployment scenario. + + :param vnf_class: The VNF class to be used. + """ + self._logger = logging.getLogger(__name__) + self._vnf_class = vnf_class + self._deployment_scenario = deployment_scenario.upper() + if self._deployment_scenario == 'P2P': + self._vnfs = [] + if self._deployment_scenario == 'PVP': + self._vnfs = [vnf_class()] + elif self._deployment_scenario == 'PVVP': + self._vnfs = [vnf_class(), vnf_class()] + self._logger.debug('__init__ ' + str(len(self._vnfs)) + + ' VNF[s] with ' + ' '.join(map(str, self._vnfs))) + def get_vnfs(self): """Returns a list of vnfs controlled by this controller. """ - raise NotImplementedError( - "The VnfController does not implement", - "the \"get_vnfs\" function.") + self._logger.debug('get_vnfs ' + str(len(self._vnfs)) + + ' VNF[s] with ' + ' '.join(map(str, self._vnfs))) + return self._vnfs - #TODO: Decide on contextmanager or __enter/exit__ strategy <MH 2015-05-01> def start(self): """Boots all VNFs set-up by __init__. This is a blocking function. """ - raise NotImplementedError( - "The VnfController does not implement", - "the \"start\" function.") + self._logger.debug('start ' + str(len(self._vnfs)) + + ' VNF[s] with ' + ' '.join(map(str, self._vnfs))) + for vnf in self._vnfs: + vnf.start() def stop(self): """Stops all VNFs set-up by __init__. This is a blocking function. """ - raise NotImplementedError( - "The VnfController does not implement", - "the \"stop\" function.") + self._logger.debug('stop ' + str(len(self._vnfs)) + + ' VNF[s] with ' + ' '.join(map(str, self._vnfs))) + for vnf in self._vnfs: + vnf.stop() + + def __enter__(self): + self.start() + + def __exit__(self, type_, value, traceback): + self.stop() diff --git a/core/vnf_controller_p2p.py b/core/vnf_controller_p2p.py deleted file mode 100644 index a881d345..00000000 --- a/core/vnf_controller_p2p.py +++ /dev/null @@ -1,64 +0,0 @@ -# Copyright 2015 Intel Corporation. -# -# 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. -"""VNF Controller for the P2P scenario -""" - -import logging - -from core.vnf_controller import IVnfController - -class VnfControllerP2P(IVnfController): - """VNF controller for the P2P scenario. - - Does nothing as there is no VNF in P2P - - Attributes: - _vnf_class: A class object representing the VNF to be used. - _deployment_scenario: A string describing the scenario to set-up in the - constructor. - _vnfs: A list of vnfs controlled by the controller. - """ - - #TODO: Decide on contextmanager or __enter/exit__ strategy <MH 2015-05-01> - def __init__(self, vnf_class): - """Sets up the VNF infrastructure for the P2P deployment scenario. - - :param vnf_class: The VNF class to be used, this is mostly ignored. - """ - self._logger = logging.getLogger(__name__) - self._vnf_class = vnf_class - self._deployment_scenario = "P2P" - self._logger.debug('__init__ with ' + str(self._vnf_class)) - - def get_vnfs(self): - """Returns an empty list of vnfs. - """ - self._logger.debug('get_vnfs with ' + str(self._vnf_class)) - return [] - - def start(self): - """Starts nothing. - """ - self._logger.debug('start with ' + str(self._vnf_class)) - - def stop(self): - """Stops nothing. - """ - self._logger.debug('stop with ' + str(self._vnf_class)) - - def __enter__(self): - self.start() - - def __exit__(self, type_, value, traceback): - self.stop() diff --git a/core/vnf_controller_pvp.py b/core/vnf_controller_pvp.py deleted file mode 100644 index 1878db10..00000000 --- a/core/vnf_controller_pvp.py +++ /dev/null @@ -1,69 +0,0 @@ -# Copyright 2015 Intel Corporation. -# -# 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. -"""VNF Controller for the PVP scenario -""" - -import logging - -from core.vnf_controller import IVnfController - -class VnfControllerPVP(IVnfController): - """VNF controller for the PVP scenario. - - Used to set-up and control a VNF provider for the PVP scenario. - - Attributes: - _vnf_class: A class object representing the VNF to be used. - _deployment_scenario: A string describing the scenario to set-up in the - constructor. - _vnfs: A list of vnfs controlled by the controller. - """ - - #TODO: Decide on contextmanager or __enter/exit__ strategy <MH 2015-05-01> - def __init__(self, vnf_class): - """Sets up the VNF infrastructure for the PVP deployment scenario. - - :param vnf_class: The VNF class to be used. - """ - self._logger = logging.getLogger(__name__) - self._vnf_class = vnf_class() - self._deployment_scenario = "PVP" - self._vnfs = [vnf_class(deployment=self._deployment_scenario)] - self._logger.debug('__init__ with ' + str(self._vnfs[0])) - #TODO call vnf.xxx to carry out the required setup - - def get_vnfs(self): - """See IVnfController for description - """ - self._logger.debug('get_vnfs with ' + str(self._vnfs[0])) - return self._vnfs - - def start(self): - """See IVnfController for description - """ - self._logger.debug('start with ' + str(self._vnfs[0])) - for vnf in self._vnfs: - vnf.start() - - def stop(self): - """See IVnfController for description - """ - self._logger.debug('stop with ' + str(self._vnfs[0])) - self._vnfs[0].stop() - - def __enter__(self): - self.start() - - def __exit__(self, type_, value, traceback): - self.stop() diff --git a/core/vswitch_controller_p2p.py b/core/vswitch_controller_p2p.py index a1158d4e..c15f7ef8 100644 --- a/core/vswitch_controller_p2p.py +++ b/core/vswitch_controller_p2p.py @@ -18,12 +18,11 @@ import logging from core.vswitch_controller import IVswitchController -from vswitches.utils import add_ports_to_flow +from conf import settings _FLOW_TEMPLATE = { 'idle_timeout': '0' } -BRIDGE_NAME = 'br0' class VswitchControllerP2P(IVswitchController): """VSwitch controller for P2P deployment scenario. @@ -53,41 +52,42 @@ class VswitchControllerP2P(IVswitchController): try: self._vswitch.start() - self._vswitch.add_switch(BRIDGE_NAME) + bridge = settings.getValue('VSWITCH_BRIDGE_NAME') + self._vswitch.add_switch(bridge) - (_, phy1_number) = self._vswitch.add_phy_port(BRIDGE_NAME) - (_, phy2_number) = self._vswitch.add_phy_port(BRIDGE_NAME) + (_, _) = self._vswitch.add_phy_port(bridge) + (_, _) = self._vswitch.add_phy_port(bridge) - self._vswitch.del_flow(BRIDGE_NAME) + self._vswitch.del_flow(bridge) # table#0 - flows designed to force 5 & 13 tuple matches go here flow = {'table':'0', 'priority':'1', 'actions': ['goto_table:1']} - self._vswitch.add_flow(BRIDGE_NAME, flow) + self._vswitch.add_flow(bridge, flow) # table#1 - flows to route packets between ports goes here. The # chosen port is communicated to subsequent tables by setting the # metadata value to the egress port number flow = {'table':'1', 'priority':'1', 'in_port':'1', 'actions': ['write_actions(output:2)', 'write_metadata:2', - 'goto_table:2']} - self._vswitch.add_flow(BRIDGE_NAME, flow) + 'goto_table:2']} + self._vswitch.add_flow(bridge, flow) flow = {'table':'1', 'priority':'1', 'in_port':'2', 'actions': ['write_actions(output:1)', 'write_metadata:1', - 'goto_table:2']} - self._vswitch.add_flow(BRIDGE_NAME, flow) + 'goto_table:2']} + self._vswitch.add_flow(bridge, flow) # Frame modification table. Frame modification flow rules are # isolated in this table so that they can be turned on or off # without affecting the routing or tuple-matching flow rules. flow = {'table':'2', 'priority':'1', 'actions': ['goto_table:3']} - self._vswitch.add_flow(BRIDGE_NAME, flow) + self._vswitch.add_flow(bridge, flow) # Egress table # (TODO) Billy O'Mahony - the drop action here actually required in # order to egress the packet. This is the subject of a thread on # ovs-discuss 2015-06-30. flow = {'table':'3', 'priority':'1', 'actions': ['drop']} - self._vswitch.add_flow(BRIDGE_NAME, flow) + self._vswitch.add_flow(bridge, flow) except: self._vswitch.stop() raise @@ -113,4 +113,4 @@ class VswitchControllerP2P(IVswitchController): """See IVswitchController for description """ self._logger.debug('get_ports_info using ' + str(self._vswitch_class)) - return self._vswitch.get_ports(BRIDGE_NAME) + return self._vswitch.get_ports(settings.getValue('VSWITCH_BRIDGE_NAME')) diff --git a/core/vswitch_controller_pvp.py b/core/vswitch_controller_pvp.py index 8c409dc2..80c0fdb2 100644 --- a/core/vswitch_controller_pvp.py +++ b/core/vswitch_controller_pvp.py @@ -19,11 +19,11 @@ import logging from core.vswitch_controller import IVswitchController from vswitches.utils import add_ports_to_flow +from conf import settings _FLOW_TEMPLATE = { 'idle_timeout': '0' } -BRIDGE_NAME = 'br0' class VswitchControllerPVP(IVswitchController): """VSwitch controller for PVP deployment scenario. @@ -54,28 +54,29 @@ class VswitchControllerPVP(IVswitchController): try: self._vswitch.start() - self._vswitch.add_switch(BRIDGE_NAME) + bridge = settings.getValue('VSWITCH_BRIDGE_NAME') + self._vswitch.add_switch(bridge) - (_, phy1_number) = self._vswitch.add_phy_port(BRIDGE_NAME) - (_, phy2_number) = self._vswitch.add_phy_port(BRIDGE_NAME) - (_, vport1_number) = self._vswitch.add_vport(BRIDGE_NAME) - (_, vport2_number) = self._vswitch.add_vport(BRIDGE_NAME) + (_, phy1_number) = self._vswitch.add_phy_port(bridge) + (_, phy2_number) = self._vswitch.add_phy_port(bridge) + (_, vport1_number) = self._vswitch.add_vport(bridge) + (_, vport2_number) = self._vswitch.add_vport(bridge) - self._vswitch.del_flow(BRIDGE_NAME) + self._vswitch.del_flow(bridge) flow1 = add_ports_to_flow(_FLOW_TEMPLATE, phy1_number, vport1_number) flow2 = add_ports_to_flow(_FLOW_TEMPLATE, vport2_number, phy2_number) - self._vswitch.add_flow(BRIDGE_NAME, flow1) - self._vswitch.add_flow(BRIDGE_NAME, flow2) + self._vswitch.add_flow(bridge, flow1) + self._vswitch.add_flow(bridge, flow2) if self._bidir: flow3 = add_ports_to_flow(_FLOW_TEMPLATE, phy2_number, vport2_number) flow4 = add_ports_to_flow(_FLOW_TEMPLATE, vport1_number, phy1_number) - self._vswitch.add_flow(BRIDGE_NAME, flow3) - self._vswitch.add_flow(BRIDGE_NAME, flow4) + self._vswitch.add_flow(bridge, flow3) + self._vswitch.add_flow(bridge, flow4) except: self._vswitch.stop() @@ -102,4 +103,4 @@ class VswitchControllerPVP(IVswitchController): """See IVswitchController for description """ self._logger.debug('get_ports_info using ' + str(self._vswitch_class)) - return self._vswitch.get_ports(BRIDGE_NAME) + return self._vswitch.get_ports(settings.getValue('VSWITCH_BRIDGE_NAME')) diff --git a/core/vswitch_controller_pvvp.py b/core/vswitch_controller_pvvp.py new file mode 100644 index 00000000..b445f9bd --- /dev/null +++ b/core/vswitch_controller_pvvp.py @@ -0,0 +1,114 @@ +# Copyright 2015 Intel Corporation. +# +# 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. + +"""VSwitch controller for Physical to VM to Physical deployment +""" + +import logging + +from core.vswitch_controller import IVswitchController +from vswitches.utils import add_ports_to_flow +from conf import settings + +_FLOW_TEMPLATE = { + 'idle_timeout': '0' +} + +class VswitchControllerPVVP(IVswitchController): + """VSwitch controller for PVVP deployment scenario. + + Attributes: + _vswitch_class: The vSwitch class to be used. + _vswitch: The vSwitch object controlled by this controller + _deployment_scenario: A string describing the scenario to set-up in the + constructor. + """ + def __init__(self, vswitch_class, bidir=False): + """Initializes up the prerequisites for the PVVP deployment scenario. + + :vswitch_class: the vSwitch class to be used. + """ + self._logger = logging.getLogger(__name__) + self._vswitch_class = vswitch_class + self._vswitch = vswitch_class() + self._deployment_scenario = "PVVP" + self._bidir = bidir + self._logger.debug('Creation using ' + str(self._vswitch_class)) + + def setup(self): + """ Sets up the switch for PVVP + """ + self._logger.debug('Setup using ' + str(self._vswitch_class)) + + try: + self._vswitch.start() + + bridge = settings.getValue('VSWITCH_BRIDGE_NAME') + self._vswitch.add_switch(bridge) + + (_, phy1_number) = self._vswitch.add_phy_port(bridge) + (_, phy2_number) = self._vswitch.add_phy_port(bridge) + (_, vport1_number) = self._vswitch.add_vport(bridge) + (_, vport2_number) = self._vswitch.add_vport(bridge) + (_, vport3_number) = self._vswitch.add_vport(bridge) + (_, vport4_number) = self._vswitch.add_vport(bridge) + + self._vswitch.del_flow(bridge) + flow1 = add_ports_to_flow(_FLOW_TEMPLATE, phy1_number, + vport1_number) + flow2 = add_ports_to_flow(_FLOW_TEMPLATE, vport2_number, + vport3_number) + flow3 = add_ports_to_flow(_FLOW_TEMPLATE, vport4_number, + phy2_number) + self._vswitch.add_flow(bridge, flow1) + self._vswitch.add_flow(bridge, flow2) + self._vswitch.add_flow(bridge, flow3) + + if self._bidir: + flow4 = add_ports_to_flow(_FLOW_TEMPLATE, phy2_number, + vport4_number) + flow5 = add_ports_to_flow(_FLOW_TEMPLATE, vport3_number, + vport2_number) + flow6 = add_ports_to_flow(_FLOW_TEMPLATE, vport1_number, + phy1_number) + self._vswitch.add_flow(bridge, flow4) + self._vswitch.add_flow(bridge, flow5) + self._vswitch.add_flow(bridge, flow6) + + except: + self._vswitch.stop() + raise + + def stop(self): + """Tears down the switch created in setup(). + """ + self._logger.debug('Stop using ' + str(self._vswitch_class)) + self._vswitch.stop() + + def __enter__(self): + self.setup() + + def __exit__(self, type_, value, traceback): + self.stop() + + def get_vswitch(self): + """See IVswitchController for description + """ + return self._vswitch + + def get_ports_info(self): + """See IVswitchController for description + """ + self._logger.debug('get_ports_info using ' + str(self._vswitch_class)) + return self._vswitch.get_ports(settings.getValue('VSWITCH_BRIDGE_NAME')) |