diff options
author | vmaffione <v.maffione@gmail.com> | 2017-03-28 15:16:10 +0000 |
---|---|---|
committer | vmaffione <v.maffione@gmail.com> | 2017-03-28 15:16:10 +0000 |
commit | 32bd8238163047f272657e124ac4949e78d2bfc6 (patch) | |
tree | 39b26c2cf3b8943d9f34d87fb9a537c0b13e860f | |
parent | 99d8c66180e24849bb4f0f7edd1be4fe852f44db (diff) | |
parent | 0e8936e55956813f7f7db633b1cb96241a78ea58 (diff) | |
download | rumba-32bd8238163047f272657e124ac4949e78d2bfc6.tar.gz rumba-32bd8238163047f272657e124ac4949e78d2bfc6.zip |
Merge branch 'master-testbeds-interface' into 'master'
testbeds: Port to new API
See merge request !14
-rw-r--r-- | rumba/model.py | 93 | ||||
-rw-r--r-- | rumba/testbeds/emulab.py | 67 | ||||
-rw-r--r-- | rumba/testbeds/faketestbed.py | 2 | ||||
-rw-r--r-- | rumba/testbeds/jfed.py | 78 | ||||
-rw-r--r-- | rumba/testbeds/qemu.py | 3 |
5 files changed, 88 insertions, 155 deletions
diff --git a/rumba/model.py b/rumba/model.py index 098930a..0659cb1 100644 --- a/rumba/model.py +++ b/rumba/model.py @@ -36,56 +36,9 @@ class Testbed: self.exp_name = exp_name @abc.abstractmethod - def create_experiment(self, nodes, links): + def create_experiment(self, experiment): raise Exception('create_experiment() not implemented') - -# Represents an interface on a node -# -# @name [string] interface name -# @ip [int] IP address of that interface -# -class Interface: - def __init__(self, name = "", ip = ""): - self.name = name - self.ip = ip - - def __repr__(self): - return self.name - -# Represents a link in the physical graph -# -# @name [string] Link name -# -class Link: - def __init__(self, name): - self.name = name - - def __repr__(self): - return self.name - -# Represents a point-to-point link in the physical graph -# -# @name [string] DIF name -# -class P2PLink(Link): - def __init__(self, name, node_a, node_b, - int_a = None, - int_b = None): - Link.__init__(self, name) - self.node_a = node_a - self.node_b = node_b - if int_a is None: - int_a = Interface() - self.int_a = int_a - if int_b is None: - int_b = Interface() - self.int_b = int_b - - def __repr__(self): - return '%s:%s--%s:%s' % (self.node_a.name, self.int_a, - self.node_b.name, self.int_b) - # Base class for DIFs # # @name [string] DIF name @@ -96,6 +49,7 @@ class DIF: if members is None: members = list() self.members = members + self.ipcps = list() def __repr__(self): s = "DIF %s" % self.name @@ -359,25 +313,6 @@ class Experiment: return s - def get_links(self): - difs = set() - links = list() - for node in self.nodes: - for dif in node.difs: - if type(dif) is ShimEthDIF: - difs.add(dif) - - for dif in difs: - # Point-to-point link - if len(dif.members) == 2: - node_a = dif.members[0] - node_b = dif.members[1] - link = P2PLink(node_a.name + "-" + node_b.name, - node_a, node_b) - links.append(link) - - return links - def add_node(self, node): self.nodes.append(node) self.generate() @@ -417,7 +352,8 @@ class Experiment: #print(difsdeps_adj) #print(difsdeps_inc_cnt) - # Run Kahn's algorithm to compute topological ordering on the DIFs graph. + # Run Kahn's algorithm to compute topological + # ordering on the DIFs graph. frontier = set() self.dif_ordering = [] for dif in difsdeps_inc_cnt: @@ -433,11 +369,13 @@ class Experiment: frontier.add(nxt) difsdeps_adj[cur] = set() - circular_set = [dif for dif in difsdeps_inc_cnt if difsdeps_inc_cnt[dif] != 0] + circular_set = [dif for dif in difsdeps_inc_cnt \ + if difsdeps_inc_cnt[dif] != 0] if len(circular_set): - raise Exception("Fatal error: The specified DIFs topology has one or more"\ - "circular dependencies, involving the following"\ - " DIFs: %s" % circular_set) + raise Exception("Fatal error: The specified DIFs topology" \ + "has one or more" \ + "circular dependencies, involving the following" \ + " DIFs: %s" % circular_set) print("DIF topological ordering: %s" % self.dif_ordering) @@ -451,8 +389,8 @@ class Experiment: dif_graphs[dif] = dict() first = None - # For each N-1-DIF supporting this DIF, compute the set of nodes that - # share such N-1-DIF. This set will be called the 'neighset' of + # For each N-1-DIF supporting this DIF, compute the set of nodes + # that share such N-1-DIF. This set will be called the 'neighset' of # the N-1-DIF for the current DIF. for node in self.nodes: @@ -482,7 +420,9 @@ class Experiment: er = [] for node in dif_graphs[dif]: for edge in dif_graphs[dif][node]: - er.append("%s --[%s]--> %s" % (node.name, edge[1].name, edge[0].name)) + er.append("%s --[%s]--> %s" % (node.name, + edge[1].name, + edge[0].name)) print("DIF graph for %s: %s" % (dif, ', '.join(er))) if self.enrollment_strategy == 'minimal': @@ -556,6 +496,7 @@ class Experiment: break node.ipcps.append(ipcp) + dif.ipcps.append(ipcp) print("IPCP for node %s: %s" % (node.name, node.ipcps)) @@ -568,7 +509,7 @@ class Experiment: # Realize the experiment, using a testbed-specific setup def swap_in(self): - self.testbed.create_experiment(self.nodes, self.get_links()) + self.testbed.create_experiment(self) @abc.abstractmethod def run(self): diff --git a/rumba/testbeds/emulab.py b/rumba/testbeds/emulab.py index cbaa730..c696fbb 100644 --- a/rumba/testbeds/emulab.py +++ b/rumba/testbeds/emulab.py @@ -37,7 +37,7 @@ warnings.filterwarnings("ignore") # class Testbed(mod.Testbed): def __init__(self, exp_name, username, password = "", - proj_name = "ARCFIRE", url = "wall1.ilabt.iminds.be", + proj_name = "ARCFIRE", url = "wall2.ilabt.iminds.be", image = "UBUNTU14-64-STD"): mod.Testbed.__init__(self, exp_name, username, password, proj_name) self.url = url @@ -101,13 +101,12 @@ class Testbed(mod.Testbed): return output - def _create_experiment(self, nodes, links): + def _create_experiment(self, experiment): ''' Creates an emulab experiment @param self: testbed info - @param nodes: holds the nodes in the experiment - @param links: holds the links in the experiment + @param experiment: the experiment ''' proj_name = self.proj_name exp_name = self.exp_name @@ -121,7 +120,7 @@ class Testbed(mod.Testbed): except: print("First experiment to be created for that project.") - ns = self.generate_ns_script(nodes, links) + ns = self.generate_ns_script(experiment) dest_file_name = '/users/'+ self.username + \ '/temp_ns_file.%s.ns' % os.getpid() ssh.copy_file_to_testbed(self, self.ops_server(), ns, dest_file_name) @@ -135,13 +134,12 @@ class Testbed(mod.Testbed): ssh.execute_command(self, self.ops_server(),'rm ' + dest_file_name) print("New experiment succesfully created.") - def generate_ns_script(self, nodes, p2plinks): + def generate_ns_script(self, experiment): ''' Generate ns script based on network graph. Enables to customize default node image. - @param nodes: holds the nodes in the experiment - @param links: holds the links in the experiment + @param experiment: the experiment @param self: testbed info @return: ns2 script for Emulab experiment @@ -151,16 +149,19 @@ class Testbed(mod.Testbed): ns2_script += "set ns [new Simulator]\n" ns2_script += "source tb_compat.tcl\n" - for node in nodes: + for node in experiment.nodes: ns2_script += "set " + node.name + " [$ns node]\n" ns2_script += "tb-set-node-os $" + node.name + " " + \ self.image + "\n" - for link in p2plinks: - ns2_script += "set " + link.name + \ + for dif in experiment.dif_ordering: + if type(dif) is mod.ShimEthDIF: + if len(dif.ipcps) != 2: + continue + ns2_script += "set " + dif.name + \ " [$ns duplex-link $" + \ - link.node_a.name + " $" + \ - link.node_b.name + " 1000Mb 0ms DropTail]\n" + dif.members[0].name + " $" + \ + dif.members[1].name + " 1000Mb 0ms DropTail]\n" ns2_script += "$ns run\n" @@ -191,16 +192,15 @@ class Testbed(mod.Testbed): print("Still waiting") time.sleep(5) - def complete_experiment_graph(self, nodes, p2plinks): + def complete_experiment_graph(self, experiment): ''' Gets the interface (ethx) to link mapping @param self: testbed info - @param nodes: holds the nodes in the experiment - @param links: holds the links in the experiment + @param experiment: the experiment ''' - node_full_name = self.full_name(nodes[0].name) + node_full_name = self.full_name(experiment.nodes[0].name) cmd = 'cat /var/emulab/boot/topomap' topomap = ssh.execute_command(self, node_full_name, cmd) # Almost as ugly as yo momma @@ -214,31 +214,28 @@ class Testbed(mod.Testbed): item2 = item2.split(':') link_name = item2[0] link_ip = item2[1] - for link in p2plinks: - if link.name == link_name: - if link.node_a.name == node_name: - link.int_a.ip = link_ip - elif link.node_b.name == node_name: - link.int_b.ip = link_ip - - for node in nodes: + for node in experiment.nodes: + if node.name != node_name: + continue + for ipcp in node.ipcps: + if ipcp.dif.name == link_name: + ipcp.ip = link_ip + + for node in experiment.nodes: cmd = 'cat /var/emulab/boot/ifmap' node_full_name = self.full_name(node.name) output = ssh.execute_command(self, node_full_name, cmd) output = re.split('\\\\n', output) for item in output: item = item.split() - for link in p2plinks: - if link.node_a.name == node.name and \ - link.int_a.ip == item[1]: - link.int_a.name = item[0] - elif link.node_b.name == node.name and \ - link.int_b.ip == item[1]: - link.int_b.name = item[0] + for ipcp in node.ipcps: + if type(ipcp) is mod.ShimEthIPCP: + if ipcp.ip == item[1]: + ipcp.ifname = item[0] node.full_name = self.full_name(node.name) - def create_experiment(self, nodes, links): - self._create_experiment(nodes, links) + def create_experiment(self, experiment): + self._create_experiment(experiment) self.swap_exp_in() self.wait_until_nodes_up() - self.complete_experiment_graph(nodes, links) + self.complete_experiment_graph(experiment) diff --git a/rumba/testbeds/faketestbed.py b/rumba/testbeds/faketestbed.py index e47eb85..8d5e724 100644 --- a/rumba/testbeds/faketestbed.py +++ b/rumba/testbeds/faketestbed.py @@ -26,5 +26,5 @@ class Testbed(mod.Testbed): password = ""): mod.Testbed.__init__(self, exp_name, username, password, proj_name) - def create_experiment(self, nodes, links): + def create_experiment(self, experiment): print("[Fake testbed] experiment swapped in") diff --git a/rumba/testbeds/jfed.py b/rumba/testbeds/jfed.py index 92e615f..04c57ba 100644 --- a/rumba/testbeds/jfed.py +++ b/rumba/testbeds/jfed.py @@ -35,7 +35,7 @@ class Testbed(mod.Testbed): self.jfed_jar = jfed_jar self.exp_hours = exp_hours - def create_rspec(self, nodes, links): + def create_rspec(self, experiment): self.rspec = self.exp_name + ".rspec" impl = xml.getDOMImplementation() @@ -66,7 +66,7 @@ class Testbed(mod.Testbed): "resources/rspec/3 http://www.geni.net/" + "resources/rspec/3/request.xsd") - for node in nodes: + for node in experiment.nodes: el = doc.createElement("node") top_el.appendChild(el) el.setAttribute("client_id", node.name) @@ -78,50 +78,41 @@ class Testbed(mod.Testbed): el2.setAttribute("name", "raw-pc") node.ifs = 0 - for link in links: - if link.node_a == node or link.node_b == node: + for ipcp in node.ipcps: + if type(ipcp) is mod.ShimEthIPCP: el3 = doc.createElement("interface") - if link.node_a == node: - link.int_a.id = node.name + ":if" + str(node.ifs) - link_id = link.int_a.id - if link.node_b == node: - link.int_b.id = node.name + ":if" + str(node.ifs) - link_id = link.int_b.id - - el3.setAttribute("client_id", link_id) + ipcp.if_id = node.name + ":if" + str(node.ifs) + el3.setAttribute("client_id", ipcp.if_id) node.ifs += 1 el.appendChild(el3) - for link in links: - el = doc.createElement("link") - top_el.appendChild(el) - el.setAttribute("client_id", link.name) - - el2 = doc.createElement("component_manager_id") - el2.setAttribute("name", self.authority) - el.appendChild(el2) + for dif in experiment.dif_ordering: + if type(dif) is mod.ShimEthDIF: + el = doc.createElement("link") + top_el.appendChild(el) + el.setAttribute("client_id", dif.name) - el3 = doc.createElement("interface_ref") - el3.setAttribute("client_id", link.int_a.id) - el.appendChild(el3) + el2 = doc.createElement("component_manager_id") + el2.setAttribute("name", self.authority) + el.appendChild(el2) - el4 = doc.createElement("interface_ref") - el4.setAttribute("client_id", link.int_b.id) - el.appendChild(el4) + for ipcp in dif.ipcps: + el3 = doc.createElement("interface_ref") + el3.setAttribute("client_id", ipcp.if_id) + el.appendChild(el3) file = open(self.rspec, "w") file.write(doc.toprettyxml()) file.close() - def create_experiment(self, nodes, links): - self.create_rspec(nodes, links) + def create_experiment(self, experiment): + self.create_rspec(experiment) self.manifest = self.exp_name + ".rrspec" - for node in nodes: + for node in experiment.nodes: auth_name_r = self.auth_name.replace(".", "-") node.full_name = node.name + "." + self.exp_name + "." + \ - self.proj_name + "." + auth_name_r + \ - "." + self.auth_name + auth_name_r + "." + self.auth_name subprocess.call(["java", "-jar", self.jfed_jar, "create", "-S", \ self.proj_name, "--rspec", \ @@ -136,17 +127,22 @@ class Testbed(mod.Testbed): rspec = xml.parse(self.manifest) xml_nodes = rspec.getElementsByTagName("node") + # Complete details of the nodes after swapin for xml_node in xml_nodes: n_name = xml_node.getAttribute("client_id") intfs = xml_node.getElementsByTagName("interface") - for link in links: - if link.node_a.name == n_name: - interface = link.int_a - if link.node_b.name == n_name: - interface = link.int_b + + for node in experiment.nodes: + if node.name == n_name: + node_n = node + for intf in intfs: - comp_id = intf.getAttribute("component_id") - comp_arr = comp_id.split(":") - interface.name = comp_arr[-1] - xml_ip = intf.getElementsByTagName("ip") - interface.ip = xml_ip[0].getAttribute("address") + i_name = intf.getAttribute("client_id") + for ipcp in node_n.ipcps: + if type(ipcp) is mod.ShimEthIPCP: + if ipcp.if_id == i_name: + comp_id = intf.getAttribute("component_id") + comp_arr = comp_id.split(":") + ipcp.ifname = comp_arr[-1] + #xml_ip = intf.getElementsByTagName("ip") + #interface.ip = xml_ip[0].getAttribute("address") diff --git a/rumba/testbeds/qemu.py b/rumba/testbeds/qemu.py index d44bb3e..3f4cb4a 100644 --- a/rumba/testbeds/qemu.py +++ b/rumba/testbeds/qemu.py @@ -26,8 +26,7 @@ class Testbed(mod.Testbed): password = ""): mod.Testbed.__init__(self, exp_name, username, password, proj_name) - def create_experiment(self, nodes, links): - print(links) + def create_experiment(self, experiment): print("[QEMU testbed] experiment swapped in") def __del__(self): |