X-Git-Url: https://gerrit.opnfv.org/gerrit/gitweb?a=blobdiff_plain;f=yardstick%2Fnetwork_services%2Fvnf_generic%2Fvnf%2Fbase.py;h=8ed754dce9b81d9a433099daa8585e91b8e33a14;hb=449679aeee27e08d5e47a7d5d76857b4827e263e;hp=955f9f03d4984d54e80453dac06f990b01d8733a;hpb=89fe59588ec6bf7da5df53cbab61731e476912c3;p=yardstick.git diff --git a/yardstick/network_services/vnf_generic/vnf/base.py b/yardstick/network_services/vnf_generic/vnf/base.py index 955f9f03d..8ed754dce 100644 --- a/yardstick/network_services/vnf_generic/vnf/base.py +++ b/yardstick/network_services/vnf_generic/vnf/base.py @@ -13,8 +13,13 @@ # limitations under the License. """ Base class implementation for generic vnf implementation """ -from __future__ import absolute_import +import abc + import logging +import six + +from yardstick.network_services.helpers.samplevnf_helper import PortPairs + LOG = logging.getLogger(__name__) @@ -59,6 +64,12 @@ class QueueFileWrapper(object): class VnfdHelper(dict): + def __init__(self, *args, **kwargs): + super(VnfdHelper, self).__init__(*args, **kwargs) + self.port_pairs = PortPairs(self['vdu'][0]['external-interface']) + # port num is not present until binding so we have to memoize + self._port_num_map = {} + @property def mgmt_interface(self): return self["mgmt-interface"] @@ -85,16 +96,54 @@ class VnfdHelper(dict): virtual_intf = interface["virtual-interface"] if virtual_intf[key] == value: return interface + raise KeyError() def find_interface(self, **kwargs): key, value = next(iter(kwargs.items())) for interface in self.interfaces: if interface[key] == value: return interface + raise KeyError() + + # hide dpdk_port_num key so we can abstract + def find_interface_by_port(self, port): + for interface in self.interfaces: + virtual_intf = interface["virtual-interface"] + # we have to convert to int to compare + if int(virtual_intf['dpdk_port_num']) == port: + return interface + raise KeyError() + + def port_num(self, port): + # we need interface name -> DPDK port num (PMD ID) -> LINK ID + # LINK ID -> PMD ID is governed by the port mask + """ + + :rtype: int + :type port: str + """ + if isinstance(port, dict): + intf = port + else: + intf = self.find_interface(name=port) + return self._port_num_map.setdefault(intf["name"], + int(intf["virtual-interface"]["dpdk_port_num"])) + + def port_nums(self, intfs): + return [self.port_num(i) for i in intfs] + + def ports_iter(self): + for port_name in self.port_pairs.all_ports: + port_num = self.port_num(port_name) + yield port_name, port_num class VNFObject(object): + # centralize network naming convention + UPLINK = PortPairs.UPLINK + DOWNLINK = PortPairs.DOWNLINK + def __init__(self, name, vnfd): super(VNFObject, self).__init__() self.name = name @@ -130,6 +179,13 @@ class GenericVNF(VNFObject): """ raise NotImplementedError() + def wait_for_instantiate(self): + """ Wait for VNF to start + + :return: True/False + """ + raise NotImplementedError() + def terminate(self): """ Kill all VNF processes @@ -154,6 +210,7 @@ class GenericVNF(VNFObject): raise NotImplementedError() +@six.add_metaclass(abc.ABCMeta) class GenericTrafficGen(GenericVNF): """ Class providing file-like API for generic traffic generator """ @@ -162,18 +219,29 @@ class GenericTrafficGen(GenericVNF): self.runs_traffic = True self.traffic_finished = False + @abc.abstractmethod def run_traffic(self, traffic_profile): - """ Generate traffic on the wire according to the given params. - Method is non-blocking, returns immediately when traffic process + """Generate traffic on the wire according to the given params. + + This method is non-blocking, returns immediately when traffic process is running. Mandatory. :param traffic_profile: :return: True/False """ - raise NotImplementedError() + + @abc.abstractmethod + def terminate(self): + """After this method finishes, all traffic processes should stop. + + Mandatory. + + :return: True/False + """ def listen_traffic(self, traffic_profile): - """ Listen to traffic with the given parameters. + """Listen to traffic with the given parameters. + Method is non-blocking, returns immediately when traffic process is running. Optional. @@ -183,16 +251,20 @@ class GenericTrafficGen(GenericVNF): pass def verify_traffic(self, traffic_profile): - """ Verify captured traffic after it has ended. Optional. + """Verify captured traffic after it has ended. + + Optional. :param traffic_profile: :return: dict """ pass - def terminate(self): - """ After this method finishes, all traffic processes should stop. Mandatory. + def wait_for_instantiate(self): + """Wait for an instance to load. + + Optional. :return: True/False """ - raise NotImplementedError() + pass