Pass code check with pylint=2.4.4 (#1012)

This commit is contained in:
lantz
2021-01-25 14:00:53 -08:00
committed by GitHub
parent 77938e0a85
commit dad451bf8f
56 changed files with 330 additions and 182 deletions
+22
View File
@@ -0,0 +1,22 @@
name: code-check
on: [push, pull_request]
jobs:
code-check:
name: Mininet Code Check
runs-on: ubuntu-latest
steps:
- name: Set up Python 3.x
uses: actions/setup-python@v2
with:
python-version: 3.x
- name: Check out Mininet source
uses: actions/checkout@v2
- name: Install Mininet code check dependencies
run: |
PYTHON=`which python` util/install.sh -n
python -m pip install pylint==2.4.4
- name: Run code check
run: make codecheck
-3
View File
@@ -24,9 +24,6 @@ jobs:
# This seems too slow unfortunately:
# sudo apt-get upgrade -y -qq
PYTHON=`which python` util/install.sh -nv
- name: Run code check (skipping for now)
run: |
bash -c "if [ `lsb_release -rs` == '14.04' ]; then make codecheck; fi"
- name: Sanity test
run: |
export sudo="sudo env PATH=$PATH"
+8 -2
View File
@@ -41,10 +41,16 @@ load-plugins=
# can either give multiple identifier separated by comma (,) or put this option
# multiple time (only on the command line, not in the configuration file where
# it should appear only once).
#
# Note: we may want to re-enable some of these at some point, but many of them
# are just style issues rather than errors.
#
disable=pointless-except, invalid-name, super-init-not-called, fixme, star-args,
too-many-instance-attributes, too-few-public-methods, too-many-arguments,
too-many-instance-attributes, too-few-public-methods,
too-many-locals, too-many-public-methods, duplicate-code, bad-whitespace,
locally-disabled, locally-enabled
locally-disabled, locally-enabled, bad-continuation,
useless-object-inheritance, unnecessary-pass, no-else-return,
no-else-raise, no-else-continue, super-with-arguments
# bad-continuation, wrong-import-order
+4 -7
View File
@@ -3,20 +3,17 @@ sudo: required
matrix:
include:
- dist: trusty
python: 2.7
env: dist="14.04 LTS trusty"
- dist: trusty
- dist: focal
python: 3.6
env: dist="14.04 LTS trusty"
env: dist="24.04 LTS focal"
before_install:
- sudo apt-get update -qq
- sudo apt-get install -qq vlan
- sudo apt-get install -qq vlan pyflakes
- PYTHON=`which python` util/install.sh -n
install:
- bash -c "if [ `lsb_release -rs` == '14.04' ]; then make codecheck; fi"
- make codecheck
- pip install pexpect || pip3 install pexpect
- util/install.sh -nfvw
+1 -1
View File
@@ -8,7 +8,7 @@ BIN = $(MN)
PYSRC = $(MININET) $(TEST) $(EXAMPLES) $(BIN)
MNEXEC = mnexec
MANPAGES = mn.1 mnexec.1
P8IGN = E251,E201,E302,E202,E126,E127,E203,E226
P8IGN = E251,E201,E302,E202,E126,E127,E203,E226,E402,W504,W503,E731
PREFIX ?= /usr
BINDIR ?= $(PREFIX)/bin
MANDIR ?= $(PREFIX)/share/man/man1
+10 -6
View File
@@ -11,15 +11,20 @@ Example to pull custom params (topo, switch, etc.) from a file:
sudo mn --custom ~/mininet/custom/custom_example.py
"""
from optparse import OptionParser
import os
import sys
import time
from functools import partial
from optparse import OptionParser # pylint: disable=deprecated-module
from sys import exit # pylint: disable=redefined-builtin
# Fix setuptools' evil madness, and open up (more?) security holes
if 'PYTHONPATH' in os.environ:
sys.path = os.environ[ 'PYTHONPATH' ].split( ':' ) + sys.path
# pylint: disable=wrong-import-position
from mininet.clean import cleanup
import mininet.cli
from mininet.log import lg, LEVELS, info, debug, warn, error, output
@@ -34,10 +39,7 @@ from mininet.link import Link, TCLink, TCULink, OVSLink
from mininet.topo import ( SingleSwitchTopo, LinearTopo,
SingleSwitchReversedTopo, MinimalTopo )
from mininet.topolib import TreeTopo, TorusTopo
from mininet.util import customClass, specialClass, splitArgs
from mininet.util import buildTopo
from functools import partial
from mininet.util import customClass, specialClass, splitArgs, buildTopo
# Experimental! cluster edition prototype
from mininet.examples.cluster import ( MininetCluster, RemoteHost,
@@ -46,6 +48,7 @@ from mininet.examples.cluster import ( MininetCluster, RemoteHost,
ClusterCleanup )
from mininet.examples.clustercli import ClusterCLI
PLACEMENT = { 'block': SwitchBinPlacer, 'random': RandomPlacer }
# built in topologies, created only when run
@@ -107,6 +110,7 @@ def nullTest( _net ):
"Null 'test' (does nothing)"
pass
TESTS.update( all=allTest, none=nullTest, build=nullTest )
# Map to alternate spellings of Mininet() methods
@@ -425,7 +429,7 @@ if __name__ == "__main__":
except KeyboardInterrupt:
info( "\n\nKeyboard Interrupt. Shutting down and cleaning up...\n\n")
cleanup()
except Exception:
except Exception: # pylint: disable=broad-except
# Print exception
type_, val_, trace_ = sys.exc_info()
errorMsg = ( "-"*80 + "\n" +
+3 -2
View File
@@ -34,14 +34,14 @@ and '/var/run'. It also has a temporary private directory mounted
on '/var/mn'
"""
from functools import partial
from mininet.net import Mininet
from mininet.node import Host
from mininet.cli import CLI
from mininet.topo import SingleSwitchTopo
from mininet.log import setLogLevel, info
from functools import partial
# Sample usage
@@ -61,6 +61,7 @@ def testHostWithPrivateDirs():
CLI( net )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
testHostWithPrivateDirs()
+38 -28
View File
@@ -74,6 +74,15 @@ Things to do:
- hifi support (e.g. delay compensation)
"""
from signal import signal, SIGINT, SIG_IGN
from subprocess import Popen, PIPE, STDOUT
import os
from random import randrange
import sys
import re
from itertools import groupby
from operator import attrgetter
from distutils.version import StrictVersion
from mininet.node import Node, Host, OVSSwitch, Controller
from mininet.link import Link, Intf
@@ -85,15 +94,7 @@ from mininet.examples.clustercli import CLI
from mininet.log import setLogLevel, debug, info, error
from mininet.clean import addCleanupCallback
from signal import signal, SIGINT, SIG_IGN
from subprocess import Popen, PIPE, STDOUT
import os
from random import randrange
import sys
import re
from itertools import groupby
from operator import attrgetter
from distutils.version import StrictVersion
# pylint: disable=too-many-arguments
def findUser():
@@ -261,7 +262,7 @@ class RemoteMixin( object ):
cmd: remote command to run (list)
**params: parameters to Popen()
returns: Popen() object"""
if type( cmd ) is str:
if isinstance( cmd, str):
cmd = cmd.split()
if self.isRemote:
if sudo:
@@ -289,6 +290,7 @@ class RemoteMixin( object ):
def addIntf( self, *args, **kwargs ):
"Override: use RemoteLink.moveIntf"
# kwargs.update( moveIntfFn=RemoteLink.moveIntf )
# pylint: disable=useless-super-delegation
return super( RemoteMixin, self).addIntf( *args, **kwargs )
@@ -325,6 +327,7 @@ class RemoteOVSSwitch( RemoteMixin, OVSSwitch ):
StrictVersion( '1.10' ) )
@classmethod
# pylint: disable=arguments-differ
def batchStartup( cls, switches, **_kwargs ):
"Start up switches in per-server batches"
key = attrgetter( 'server' )
@@ -336,6 +339,7 @@ class RemoteOVSSwitch( RemoteMixin, OVSSwitch ):
return switches
@classmethod
# pylint: disable=arguments-differ
def batchShutdown( cls, switches, **_kwargs ):
"Stop switches in per-server batches"
key = attrgetter( 'server' )
@@ -413,8 +417,9 @@ class RemoteLink( Link ):
# And we can't ssh into this server remotely as 'localhost',
# so try again swappping node1 and node2
if node2.server == 'localhost':
return self.makeTunnel( node2, node1, intfname2, intfname1,
addr2, addr1 )
return self.makeTunnel( node1=node2, node2=node1,
intfname1=intfname2, intfname2=intfname1,
addr1=addr2, addr2=addr1 )
debug( '\n*** Make SSH tunnel ' + node1.server + ':' + intfname1 +
' == ' + node2.server + ':' + intfname2 )
# 1. Create tap interfaces
@@ -526,8 +531,9 @@ class RemoteGRELink( RemoteLink ):
# We should never try to create a tunnel to ourselves!
assert node1.server != node2.server
if node2.server == 'localhost':
return self.makeTunnel( node2, node1, intfname2, intfname1,
addr2, addr1 )
return self.makeTunnel( node1=node2, node2=node1,
intfname1=intfname2, intfname2=intfname1,
addr1=addr2, addr2=addr1 )
IP1, IP2 = node1.serverIP, node2.serverIP
# GRE tunnel needs to be set up with the IP of the local interface
# that connects the remote node, NOT '127.0.0.1' of localhost
@@ -555,6 +561,7 @@ class RemoteGRELink( RemoteLink ):
node.rcmd('ip link set dev %s mtu 1450' % intfname)
if not self.moveIntf(intfname, node):
raise Exception('interface move failed on node %s' % node)
return None # May want to return something useful here
# Some simple placement algorithms for MininetCluster
@@ -589,10 +596,10 @@ class Placer( object ):
class RandomPlacer( Placer ):
"Random placement"
def place( self, nodename ):
def place( self, node ):
"""Random placement function
nodename: node name"""
assert nodename # please pylint
node: node"""
assert node # please pylint
# This may be slow with lots of servers
return self.servers[ randrange( 0, len( self.servers ) ) ]
@@ -606,10 +613,10 @@ class RoundRobinPlacer( Placer ):
Placer.__init__( self, *args, **kwargs )
self.next = 0
def place( self, nodename ):
def place( self, node ):
"""Round-robin placement function
nodename: node name"""
assert nodename # please pylint
node: node"""
assert node # please pylint
# This may be slow with lots of servers
server = self.servers[ self.next ]
self.next = ( self.next + 1 ) % len( self.servers )
@@ -647,7 +654,7 @@ class SwitchBinPlacer( Placer ):
tickets = sum( [ binsizes[ server ] * [ server ]
for server in servers ], [] )
# And assign one ticket to each node
return { node: ticket for node, ticket in zip( nodes, tickets ) }
return dict( zip( nodes, tickets ) )
def calculatePlacement( self ):
"Pre-calculate node placement"
@@ -704,21 +711,21 @@ class HostSwitchBinPlacer( Placer ):
self.cset = frozenset( self.controllers )
self.hind, self.sind, self.cind = 0, 0, 0
def place( self, nodename ):
def place( self, node ):
"""Simple placement algorithm:
place nodes into evenly sized bins"""
# Place nodes into bins
if nodename in self.hset:
if node in self.hset:
server = self.servdict[ self.hind / self.hbin ]
self.hind += 1
elif nodename in self.sset:
elif node in self.sset:
server = self.servdict[ self.sind / self.sbin ]
self.sind += 1
elif nodename in self.cset:
elif node in self.cset:
server = self.servdict[ self.cind / self.cbin ]
self.cind += 1
else:
info( 'warning: unknown node', nodename )
info( 'warning: unknown node', node )
server = self.servdict[ 0 ]
return server
@@ -764,6 +771,7 @@ class MininetCluster( Mininet ):
# Make sure control directory exists
self.cdir = os.environ[ 'HOME' ] + '/.ssh/mn'
errRun( [ 'mkdir', '-p', self.cdir ] )
# pylint: disable=unexpected-keyword-arg
Mininet.__init__( self, *args, **params )
def popen( self, cmd ):
@@ -840,18 +848,19 @@ class MininetCluster( Mininet ):
if cfile:
config.setdefault( 'controlPath', cfile )
# pylint: disable=arguments-differ,signature-differs
def addController( self, *args, **kwargs ):
"Patch to update IP address to global IP address"
controller = Mininet.addController( self, *args, **kwargs )
loopback = '127.0.0.1'
if ( not isinstance( controller, Controller ) or
controller.IP() != loopback ):
return
return None
# Find route to a different server IP address
serverIPs = [ ip for ip in self.serverIP.values()
if ip is not controller.IP() ]
if not serverIPs:
return # no remote servers - loopback is fine
return None # no remote servers - loopback is fine
remoteIP = serverIPs[ 0 ]
# Route should contain 'dev <intfname>'
route = controller.cmd( 'ip route get', remoteIP,
@@ -865,6 +874,7 @@ class MininetCluster( Mininet ):
debug( controller, 'IP address updated to', controller.IP() )
return controller
# pylint: disable=arguments-differ,signature-differs
def buildFromTopo( self, *args, **kwargs ):
"Start network"
info( '*** Placing nodes\n' )
+1
View File
@@ -17,6 +17,7 @@ def clusterSanity():
CLI( net )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
clusterSanity()
+1
View File
@@ -31,6 +31,7 @@ class ClusterCLI( CLI ):
if not nx:
try:
# pylint: disable=import-error,no-member
# pylint: disable=import-outside-toplevel
import networkx
nx = networkx # satisfy pylint
from matplotlib import pyplot
+1
View File
@@ -19,6 +19,7 @@ def demo():
CLI( net )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
demo()
+1
View File
@@ -17,6 +17,7 @@ def perf(Link):
net.iperf()
net.stop()
if __name__ == '__main__':
setLogLevel('info')
perf( RemoteSSHLink )
+4
View File
@@ -27,6 +27,7 @@ Bob Lantz, April 2010
import re
# pylint: disable=import-error
from Tkinter import Frame, Button, Label, Text, Scrollbar, Canvas, Wm, READABLE
from mininet.log import setLogLevel
@@ -34,6 +35,9 @@ from mininet.topolib import TreeNet
from mininet.term import makeTerms, cleanUpScreens
from mininet.util import quietRun
# pylint: disable=too-many-arguments
class Console( Frame ):
"A simple console on a host."
+1
View File
@@ -26,6 +26,7 @@ class MultiSwitch( OVSSwitch ):
def start( self, controllers ):
return OVSSwitch.start( self, [ cmap[ self.name ] ] )
topo = TreeTopo( depth=2, fanout=2 )
net = Mininet( topo=topo, switch=MultiSwitch, build=False, waitConnected=True )
for c in [ c0, c1 ]:
+1
View File
@@ -58,6 +58,7 @@ def multiControllerNet():
info( "*** Stopping network\n" )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' ) # for CLI output
multiControllerNet()
+2
View File
@@ -66,6 +66,7 @@ class MininetFacade( object ):
for net in self.nets:
if key in net:
return net[ key ]
return None
def __iter__( self ):
"Iterate through all nodes in all Mininet objects"
@@ -100,6 +101,7 @@ class MininetFacade( object ):
class ControlNetwork( Topo ):
"Control Network Topology"
# pylint: disable=arguments-differ
def build( self, n, dataController=DataController, **_kwargs ):
"""n: number of data network controller nodes
dataController: class for data network controllers"""
+1 -1
View File
@@ -54,7 +54,7 @@ def bwtest( cpuLimits, period_us=100000, seconds=10 ):
try:
net = Mininet( topo=topo, host=host, waitConnected=True )
# pylint: disable=bare-except
except:
except: # noqa
info( '*** Skipping scheduler %s and cleaning up\n' % sched )
cleanup()
break
+1
View File
@@ -39,6 +39,7 @@ def emptyNet():
info( '*** Stopping network' )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
emptyNet()
+4
View File
@@ -8,6 +8,8 @@ hardware interface) to a network after the network is created.
import re
import sys
from sys import exit # pylint: disable=redefined-builtin
from mininet.cli import CLI
from mininet.log import setLogLevel, info, error
from mininet.net import Mininet
@@ -15,6 +17,7 @@ from mininet.link import Intf
from mininet.topolib import TreeTopo
from mininet.util import quietRun
def checkIntf( intf ):
"Make sure intf exists and is not configured."
config = quietRun( 'ifconfig %s 2>/dev/null' % intf, shell=True )
@@ -27,6 +30,7 @@ def checkIntf( intf ):
'and is probably in use!\n' )
exit( 1 )
if __name__ == '__main__':
setLogLevel( 'info' )
+1
View File
@@ -43,6 +43,7 @@ def intfOptions():
info( '\n*** Done testing\n' )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
intfOptions()
+1
View File
@@ -55,6 +55,7 @@ def verySimpleLimit( bw=150 ):
h2.cmdPrint( 'tc -d class show dev', h2.defaultIntf() )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
limit()
+9 -4
View File
@@ -24,20 +24,24 @@ of switches, this example demonstrates:
"""
import sys
from functools import partial
from mininet.net import Mininet
from mininet.node import UserSwitch, OVSKernelSwitch, Controller
from mininet.topo import Topo
from mininet.log import lg, info
from mininet.util import irange, quietRun
from mininet.link import TCLink
from functools import partial
import sys
flush = sys.stdout.flush
class LinearTestTopo( Topo ):
"Topology for a string of N hosts and N-1 switches."
# pylint: disable=arguments-differ
def build( self, N, **params ):
# Create switches and hosts
hosts = [ self.addHost( 'h%s' % h )
@@ -79,7 +83,7 @@ def linearBandwidthTest( lengths ):
output = quietRun( 'sysctl -w net.ipv4.tcp_congestion_control=reno' )
assert 'reno' in output
for datapath in switches.keys():
for datapath in switches:
info( "*** testing", datapath, "datapath\n" )
Switch = switches[ datapath ]
results[ datapath ] = []
@@ -105,7 +109,7 @@ def linearBandwidthTest( lengths ):
results[ datapath ] += [ ( n, serverbw ) ]
net.stop()
for datapath in switches.keys():
for datapath in switches:
info( "\n*** Linear network results for", datapath, "datapath:\n" )
result = results[ datapath ]
info( "SwitchCount\tiperf Results\n" )
@@ -115,6 +119,7 @@ def linearBandwidthTest( lengths ):
info( '\n')
info( '\n' )
if __name__ == '__main__':
lg.setLogLevel( 'info' )
sizes = [ 1, 2, 3, 4 ]
+3
View File
@@ -38,6 +38,7 @@ from mininet.cli import CLI
class LinuxRouter( Node ):
"A Node with IP forwarding enabled."
# pylint: disable=arguments-differ
def config( self, **params ):
super( LinuxRouter, self).config( **params )
# Enable forwarding on the router
@@ -51,6 +52,7 @@ class LinuxRouter( Node ):
class NetworkTopo( Topo ):
"A LinuxRouter connecting three IP subnets"
# pylint: disable=arguments-differ
def build( self, **_opts ):
defaultIP = '192.168.1.1/24' # IP address for r0-eth1
@@ -87,6 +89,7 @@ def run():
CLI( net )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
run()
+64 -59
View File
@@ -1,4 +1,4 @@
#!/usr/bin/python
#!/usr/bin/env python
"""
MiniEdit: a simple network editor for Mininet
@@ -13,16 +13,30 @@ Controller icon from http://semlabs.co.uk/
OpenFlow icon from https://www.opennetworking.org/
"""
# Miniedit needs some work in order to pass pylint...
# pylint: disable=line-too-long,too-many-branches
# pylint: disable=too-many-statements,attribute-defined-outside-init
# pylint: disable=missing-docstring
MINIEDIT_VERSION = '2.2.0.1'
import json
import os
import re
import sys
from distutils.version import StrictVersion
from functools import partial
from optparse import OptionParser
from subprocess import call
from sys import exit # pylint: disable=redefined-builtin
from mininet.log import info, debug, warn, setLogLevel
from mininet.net import Mininet, VERSION
from mininet.util import (netParse, ipAdd, quietRun,
buildTopo, custom, customClass )
from mininet.term import makeTerm, cleanUpScreens
from mininet.node import (Controller, RemoteController, NOX, OVSController,
CPULimitedHost, Host, Node,
OVSSwitch, UserSwitch, IVSSwitch )
from mininet.link import TCLink, Intf, Link
from mininet.cli import CLI
from mininet.moduledeps import moduleDeps
from mininet.topo import SingleSwitchTopo, LinearTopo, SingleSwitchReversedTopo
from mininet.topolib import TreeTopo
# pylint: disable=import-error
if sys.version_info[0] == 2:
@@ -47,38 +61,24 @@ else:
from tkinter import font as tkFont
from tkinter import simpledialog as tkSimpleDialog
from tkinter import filedialog as tkFileDialog
# someday: from ttk import *
# pylint: enable=import-error
import re
import json
from distutils.version import StrictVersion
import os
from functools import partial
# Miniedit still needs work in order to pass pylint...
# pylint: disable=line-too-long,too-many-branches
# pylint: disable=too-many-statements,attribute-defined-outside-init
# pylint: disable=missing-docstring,too-many-ancestors
# pylint: disable=too-many-nested-blocks,too-many-arguments
MINIEDIT_VERSION = '2.2.0.1'
if 'PYTHONPATH' in os.environ:
sys.path = os.environ[ 'PYTHONPATH' ].split( ':' ) + sys.path
# someday: from ttk import *
from mininet.log import info, debug, warn, setLogLevel
from mininet.net import Mininet, VERSION
from mininet.util import netParse, ipAdd, quietRun
from mininet.util import buildTopo
from mininet.util import custom, customClass
from mininet.term import makeTerm, cleanUpScreens
from mininet.node import Controller, RemoteController, NOX, OVSController
from mininet.node import CPULimitedHost, Host, Node
from mininet.node import OVSSwitch, UserSwitch
from mininet.link import TCLink, Intf, Link
from mininet.cli import CLI
from mininet.moduledeps import moduleDeps
from mininet.topo import SingleSwitchTopo, LinearTopo, SingleSwitchReversedTopo
from mininet.topolib import TreeTopo
info( 'MiniEdit running against Mininet '+VERSION, '\n' )
MININET_VERSION = re.sub(r'[^\d\.]', '', VERSION)
if StrictVersion(MININET_VERSION) > StrictVersion('2.0'):
from mininet.node import IVSSwitch
TOPODEF = 'none'
TOPOS = { 'minimal': lambda: SingleSwitchTopo( k=2 ),
@@ -138,6 +138,7 @@ class LegacyRouter( Node ):
def __init__( self, name, inNamespace=True, **params ):
Node.__init__( self, name, inNamespace, **params )
# pylint: disable=arguments-differ
def config( self, **_params ):
if self.intfs:
self.setParam( _params, 'setIP', ip='0.0.0.0' )
@@ -818,8 +819,8 @@ class VerticalScrolledTable(LabelFrame):
* This frame only allows vertical scrolling
"""
def __init__(self, parent, rows=2, columns=2, title=None, *args, **kw):
LabelFrame.__init__(self, parent, text=title, padx=5, pady=5, *args, **kw)
def __init__(self, parent, rows=2, columns=2, title=None, **kw):
LabelFrame.__init__(self, parent, text=title, padx=5, pady=5, **kw)
# create a canvas object and a vertical scrollbar for scrolling it
vscrollbar = Scrollbar(self, orient=VERTICAL)
@@ -855,8 +856,6 @@ class VerticalScrolledTable(LabelFrame):
canvas.itemconfigure(interior_id, width=canvas.winfo_width())
canvas.bind('<Configure>', _configure_canvas)
return
class TableFrame(Frame):
def __init__(self, parent, rows=2, columns=2):
@@ -888,7 +887,7 @@ class TableFrame(Frame):
label.grid(row=self.rows, column=column, sticky="wens", padx=1, pady=1)
if value is not None:
label.insert(0, value[column])
if readonly == True:
if readonly:
label.configure(state='readonly')
current_row.append(label)
self._widgets.append(current_row)
@@ -1401,11 +1400,11 @@ class MiniEdit( Frame ):
def addNode( self, node, nodeNum, x, y, name=None):
"Add a new node to our canvas."
if 'Switch' == node:
if node == 'Switch':
self.switchCount += 1
if 'Host' == node:
if node == 'Host':
self.hostCount += 1
if 'Controller' == node:
if node == 'Controller':
self.controllerCount += 1
if name is None:
name = self.nodePrefixes[ node ] + nodeNum
@@ -1422,13 +1421,16 @@ class MiniEdit( Frame ):
def convertJsonUnicode(self, text):
"Some part of Mininet don't like Unicode"
try:
unicode
except NameError:
return text
if isinstance(text, dict):
return {self.convertJsonUnicode(key): self.convertJsonUnicode(value) for key, value in text.items()}
elif isinstance(text, list):
if isinstance(text, list):
return [self.convertJsonUnicode(element) for element in text]
elif isinstance(text, unicode):
if isinstance(text, unicode): # pylint: disable=undefined-variable
return text.encode('utf-8')
else:
return text
def loadTopology( self ):
@@ -1440,7 +1442,7 @@ class MiniEdit( Frame ):
('All Files','*'),
]
f = tkFileDialog.askopenfile(filetypes=myFormats, mode='rb')
if f == None:
if f is None:
return
self.newTopology()
loadedTopology = self.convertJsonUnicode(json.load(f))
@@ -1601,10 +1603,11 @@ class MiniEdit( Frame ):
for widget in self.widgetToItem:
if name == widget[ 'text' ]:
return widget
return None
def newTopology( self ):
"New command."
for widget in self.widgetToItem.keys():
for widget in self.widgetToItem:
self.deleteItem( self.widgetToItem[ widget ] )
self.hostCount = 0
self.switchCount = 0
@@ -1725,7 +1728,7 @@ class MiniEdit( Frame ):
if controllerType == 'inband':
inBandCtrl = True
if inBandCtrl == True:
if inBandCtrl:
f.write("\n")
f.write("class InbandController( RemoteController ):\n")
f.write("\n")
@@ -2122,7 +2125,7 @@ class MiniEdit( Frame ):
c = self.canvas
x, y = c.canvasx( event.x ), c.canvasy( event.y )
name = self.nodePrefixes[ node ]
if 'Switch' == node:
if node == 'Switch':
self.switchCount += 1
name = self.nodePrefixes[ node ] + str( self.switchCount )
self.switchOpts[name] = {}
@@ -2130,14 +2133,14 @@ class MiniEdit( Frame ):
self.switchOpts[name]['hostname']=name
self.switchOpts[name]['switchType']='default'
self.switchOpts[name]['controllers']=[]
if 'LegacyRouter' == node:
if node == 'LegacyRouter':
self.switchCount += 1
name = self.nodePrefixes[ node ] + str( self.switchCount )
self.switchOpts[name] = {}
self.switchOpts[name]['nodeNum']=self.switchCount
self.switchOpts[name]['hostname']=name
self.switchOpts[name]['switchType']='legacyRouter'
if 'LegacySwitch' == node:
if node == 'LegacySwitch':
self.switchCount += 1
name = self.nodePrefixes[ node ] + str( self.switchCount )
self.switchOpts[name] = {}
@@ -2145,13 +2148,13 @@ class MiniEdit( Frame ):
self.switchOpts[name]['hostname']=name
self.switchOpts[name]['switchType']='legacySwitch'
self.switchOpts[name]['controllers']=[]
if 'Host' == node:
if node == 'Host':
self.hostCount += 1
name = self.nodePrefixes[ node ] + str( self.hostCount )
self.hostOpts[name] = {'sched':'host'}
self.hostOpts[name]['nodeNum']=self.hostCount
self.hostOpts[name]['hostname']=name
if 'Controller' == node:
if node == 'Controller':
name = self.nodePrefixes[ node ] + str( self.controllerCount )
ctrlr = { 'controllerType': 'ref',
'hostname': name,
@@ -2169,15 +2172,15 @@ class MiniEdit( Frame ):
self.itemToWidget[ item ] = icon
self.selectItem( item )
icon.links = {}
if 'Switch' == node:
if node == 'Switch':
icon.bind('<Button-3>', self.do_switchPopup )
if 'LegacyRouter' == node:
if node == 'LegacyRouter':
icon.bind('<Button-3>', self.do_legacyRouterPopup )
if 'LegacySwitch' == node:
if node == 'LegacySwitch':
icon.bind('<Button-3>', self.do_legacySwitchPopup )
if 'Host' == node:
if node == 'Host':
icon.bind('<Button-3>', self.do_hostPopup )
if 'Controller' == node:
if node == 'Controller':
icon.bind('<Button-3>', self.do_controllerPopup )
def clickController( self, event ):
@@ -2374,6 +2377,8 @@ class MiniEdit( Frame ):
# For now, don't allow hosts to be directly linked
stags = self.canvas.gettags( self.widgetToItem[ source ] )
dtags = self.canvas.gettags( target )
# TODO: Make this less confusing
# pylint: disable=too-many-boolean-expressions
if (('Host' in stags and 'Host' in dtags) or
('Controller' in dtags and 'LegacyRouter' in stags) or
('Controller' in stags and 'LegacyRouter' in dtags) or
@@ -3225,7 +3230,8 @@ class MiniEdit( Frame ):
"Parse custom file and add params before parsing cmd-line options."
customs = {}
if os.path.isfile( fileName ):
execfile( fileName, customs, customs )
with open( fileName, 'r' ) as f:
exec( f.read() ) # pylint: disable=exec-used
for name, val in customs.items():
self.setCustom( name, val )
else:
@@ -3592,8 +3598,7 @@ def addDictOption( opts, choicesDict, default, name, helpStr=None ):
if __name__ == '__main__':
setLogLevel( 'info' )
app = MiniEdit()
### import topology if specified ###
app.parseArgs()
### import topology if specified ###
app.importTopo()
app.mainloop()
+3 -2
View File
@@ -19,14 +19,13 @@ to-do:
- think about clearing last hop - why doesn't that work?
"""
from random import randint
from mininet.net import Mininet
from mininet.node import OVSSwitch
from mininet.topo import LinearTopo
from mininet.log import info, output, warn, setLogLevel
from random import randint
class MobilitySwitch( OVSSwitch ):
"Switch that can reattach and rename interfaces"
@@ -38,6 +37,7 @@ class MobilitySwitch( OVSSwitch ):
del self.intfs[ port ]
del self.nameToIntf[ intf.name ]
# pylint: disable=arguments-differ
def addIntf( self, intf, rename=False, **kwargs ):
"Add (and reparent) an interface"
OVSSwitch.addIntf( self, intf, **kwargs )
@@ -132,6 +132,7 @@ def mobilityTest():
old = new
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
mobilityTest()
+2
View File
@@ -21,6 +21,7 @@ def runMultiLink():
class simpleMultiLinkTopo( Topo ):
"Simple topology with multiple links"
# pylint: disable=arguments-differ
def build( self, n, **_kwargs ):
h1, h2 = self.addHost( 'h1' ), self.addHost( 'h2' )
s1 = self.addSwitch( 's1' )
@@ -29,6 +30,7 @@ class simpleMultiLinkTopo( Topo ):
self.addLink( s1, h1 )
self.addLink( s1, h2 )
if __name__ == '__main__':
setLogLevel( 'info' )
runMultiLink()
+2 -2
View File
@@ -8,14 +8,14 @@ multiple hosts and monitor their output interactively for a period=
of time.
"""
from select import poll, POLLIN
from time import time
from mininet.net import Mininet
from mininet.node import Node
from mininet.topo import SingleSwitchTopo
from mininet.log import info, setLogLevel
from select import poll, POLLIN
from time import time
def chunks( l, n ):
"Divide list l into chunks of size n - thanks Stackoverflow"
+4 -4
View File
@@ -6,15 +6,15 @@ monitoring them
"""
from time import time
from select import poll, POLLIN
from subprocess import Popen, PIPE
from mininet.topo import SingleSwitchTopo
from mininet.net import Mininet
from mininet.log import info, setLogLevel
from mininet.util import decode
from time import time
from select import poll, POLLIN
from subprocess import Popen, PIPE
def monitorFiles( outfiles, seconds, timeoutms ):
"Monitor set of files and return [(host, line)...]"
+1
View File
@@ -17,6 +17,7 @@ def ifconfigTest( net ):
for host in hosts:
info( host.cmd( 'ifconfig' ) )
if __name__ == '__main__':
lg.setLogLevel( 'info' )
info( "*** Initializing Mininet and kernel modules\n" )
+2
View File
@@ -27,6 +27,7 @@ from mininet.util import irange
class InternetTopo(Topo):
"Single switch connected to n hosts."
# pylint: disable=arguments-differ
def build(self, n=2, **_kwargs ):
# set up inet switch
inetSwitch = self.addSwitch('s0')
@@ -62,6 +63,7 @@ def run():
CLI(net)
net.stop()
if __name__ == '__main__':
setLogLevel('info')
run()
+1
View File
@@ -75,6 +75,7 @@ def testPortNumbering():
info( '*** Stopping network\n' )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
testPortNumbering()
+1
View File
@@ -28,6 +28,7 @@ def monitorhosts( hosts=5 ):
# Done
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
monitorhosts( hosts=5 )
+4 -2
View File
@@ -2,13 +2,14 @@
"Monitor multiple hosts using popen()/pmonitor()"
from time import time
from signal import SIGINT
from mininet.net import Mininet
from mininet.topo import SingleSwitchTopo
from mininet.util import pmonitor
from mininet.log import setLogLevel, info
from time import time
from signal import SIGINT
def pmonitorTest( N=3, seconds=10 ):
"Run pings and monitor multiple hosts using pmonitor"
@@ -31,6 +32,7 @@ def pmonitorTest( N=3, seconds=10 ):
p.send_signal( SIGINT )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
pmonitorTest()
+2 -1
View File
@@ -8,6 +8,7 @@ but it exposes the configuration details and allows customization.
For most tasks, the higher-level API will be preferable.
"""
from time import sleep
from mininet.net import Mininet
from mininet.node import Node
@@ -15,7 +16,6 @@ from mininet.link import Link
from mininet.log import setLogLevel, info
from mininet.util import quietRun
from time import sleep
def scratchNet( cname='controller', cargs='-v ptcp:' ):
"Create network from scratch using Open vSwitch."
@@ -62,6 +62,7 @@ def scratchNet( cname='controller', cargs='-v ptcp:' ):
switch.deleteIntfs()
info( '\n' )
if __name__ == '__main__':
setLogLevel( 'info' )
info( '*** Scratch network demo (kernel datapath)\n' )
+1
View File
@@ -66,6 +66,7 @@ def scratchNetUser( cname='controller', cargs='ptcp:' ):
switch.deleteIntfs()
info( '\n' )
if __name__ == '__main__':
setLogLevel( 'info' )
info( '*** Scratch network demo (user datapath)\n' )
+2 -1
View File
@@ -9,6 +9,7 @@ iperf will hang indefinitely if the TCP handshake fails
to complete.
"""
from sys import argv
from mininet.topo import Topo
from mininet.net import Mininet
@@ -17,7 +18,6 @@ from mininet.link import TCLink
from mininet.util import dumpNodeConnections
from mininet.log import setLogLevel, info
from sys import argv
# It would be nice if we didn't have to do this:
# pylint: disable=arguments-differ
@@ -54,6 +54,7 @@ def perfTest( lossy=True ):
net.iperf( ( h1, h4 ), l4Type='UDP' )
net.stop()
if __name__ == '__main__':
setLogLevel( 'info' )
# Prevent test_simpleperf from failing due to packet loss
+2
View File
@@ -47,6 +47,7 @@ def connectToRootNS( network, switch, ip, routes ):
for route in routes:
root.cmd( 'route add -net ' + route + ' dev ' + str( intf ) )
# pylint: disable=too-many-arguments
def sshd( network, cmd='/usr/sbin/sshd', opts='-D',
ip='10.123.123.1/32', routes=None, switch=None ):
"""Start a network, connect it to root ns, and run sshd on all hosts.
@@ -73,6 +74,7 @@ def sshd( network, cmd='/usr/sbin/sshd', opts='-D',
host.cmd( 'kill %' + cmd )
network.stop()
if __name__ == '__main__':
lg.setLogLevel( 'info')
net = TreeNet( depth=1, fanout=4 )
+1
View File
@@ -38,6 +38,7 @@ def treePing64():
info( "%s: %d%% packet loss\n" % ( name, results[ name ] ) )
info( '\n' )
if __name__ == '__main__':
setLogLevel( 'info' )
treePing64()
+6
View File
@@ -24,14 +24,18 @@ Usage (example uses VLAN ID=1000):
"""
from sys import exit # pylint: disable=redefined-builtin
from mininet.node import Host
from mininet.topo import Topo
from mininet.util import quietRun
from mininet.log import error
class VLANHost( Host ):
"Host connected to VLAN interface"
# pylint: disable=arguments-differ
def config( self, vlan=100, **params ):
"""Configure VLANHost according to (optional) parameters:
vlan: VLAN ID for default interface"""
@@ -54,6 +58,7 @@ class VLANHost( Host ):
return r
hosts = { 'vlan': VLANHost }
@@ -101,6 +106,7 @@ def exampleCustomTags():
CLI( net )
net.stop()
if __name__ == '__main__':
import sys
from functools import partial
+8 -5
View File
@@ -47,7 +47,7 @@ class CLI( Cmd ):
prompt = 'mininet> '
def __init__( self, mininet, stdin=sys.stdin, script=None,
*args, **kwargs ):
**kwargs ):
"""Start and run interactive or batch mode CLI
mininet: Mininet network object
stdin: standard input for CLI
@@ -59,7 +59,7 @@ class CLI( Cmd ):
self.inPoller = poll()
self.inPoller.register( stdin )
self.inputFile = script
Cmd.__init__( self, *args, stdin=stdin, **kwargs )
Cmd.__init__( self, stdin=stdin, **kwargs )
info( '*** Starting CLI:\n' )
if self.inputFile:
@@ -79,6 +79,7 @@ class CLI( Cmd ):
return
cls.readlineInited = True
try:
# pylint: disable=import-outside-toplevel
from readline import ( read_history_file, write_history_file,
set_history_length )
except ImportError:
@@ -141,7 +142,7 @@ class CLI( Cmd ):
' mininet> xterm h2\n\n'
)
def do_help( self, line ):
def do_help( self, line ): # pylint: disable=arguments-differ
"Describe available CLI commands."
Cmd.do_help( self, line )
if line == '':
@@ -173,6 +174,7 @@ class CLI( Cmd ):
"""Evaluate a Python expression.
Node names may be used, e.g.: py h1.cmd('ls')"""
try:
# pylint: disable=eval-used
result = eval( line, globals(), self.getLocals() )
if not result:
return
@@ -467,10 +469,10 @@ class CLI( Cmd ):
node.sendInt()
except select.error as e:
# pylint: disable=unpacking-non-sequence
# pylint: disable=unbalanced-tuple-unpacking
errno_, errmsg = e.args
# pylint: enable=unpacking-non-sequence
if errno_ != errno.EINTR:
error( "select.error: %d, %s" % (errno_, errmsg) )
error( "select.error: %s, %s" % (errno_, errmsg) )
node.sendInt()
def precmd( self, line ):
@@ -488,3 +490,4 @@ def isReadable( poller ):
mask = fdmask[ 1 ]
if mask & POLLIN:
return True
return False
+14 -3
View File
@@ -24,9 +24,14 @@ TCIntf: interface with bandwidth limiting and delay via tc
Link: basic link class for creating veth pairs
"""
import re
from mininet.log import info, error, debug
from mininet.util import makeIntfPair
import re
# Make pylint happy:
# pylint: disable=too-many-arguments
class Intf( object ):
@@ -170,7 +175,7 @@ class Intf( object ):
name, value = list( param.items() )[ 0 ]
f = getattr( self, method, None )
if not f or value is None:
return
return None
if isinstance( value, list ):
result = f( *value )
elif isinstance( value, dict ):
@@ -311,6 +316,7 @@ class TCIntf( Intf ):
debug(" *** executing command: %s\n" % c)
return self.cmd( c )
# pylint: disable=arguments-differ
def config( self, bw=None, delay=None, jitter=None, loss=None,
gro=False, txo=True, rxo=True,
speedup=0, use_hfsc=False, use_tbf=False,
@@ -351,7 +357,7 @@ class TCIntf( Intf ):
# Question: what happens if we want to reset things?
if ( bw is None and not delay and not loss
and max_queue_size is None ):
return
return None
# Clear existing configuration
tcoutput = self.tc( '%s qdisc show dev %s' )
@@ -533,6 +539,10 @@ class OVSLink( Link ):
def __init__( self, node1, node2, **kwargs ):
"See Link.__init__() for options"
try:
OVSSwitch
except NameError:
# pylint: disable=import-outside-toplevel,cyclic-import
from mininet.node import OVSSwitch
self.isPatchLink = False
if ( isinstance( node1, OVSSwitch ) and
@@ -541,6 +551,7 @@ class OVSLink( Link ):
kwargs.update( cls1=OVSIntf, cls2=OVSIntf )
Link.__init__( self, node1, node2, **kwargs )
# pylint: disable=arguments-differ, signature-differs
def makeIntfPair( self, *args, **kwargs ):
"Usually delegated to OVSSwitch"
if self.isPatchLink:
+4 -2
View File
@@ -51,7 +51,7 @@ class StreamHandlerNoNewline( logging.StreamHandler ):
self.flush()
except ( KeyboardInterrupt, SystemExit ):
raise
except:
except: # noqa pylint: disable=bare-except
self.handleError( record )
@@ -137,13 +137,14 @@ class MininetLogger( Logger, object ):
logger.warning("Houston, we have a %s", "cli output", exc_info=1)
"""
if self.manager.disable >= OUTPUT:
if getattr( self.manager, 'disabled', 0 ) >= OUTPUT:
return
if self.isEnabledFor( OUTPUT ):
self._log( OUTPUT, msg, args, kwargs )
# pylint: enable=method-hidden
lg = MininetLogger()
# Make things a bit more convenient by adding aliases
@@ -168,6 +169,7 @@ def makeListCompatible( fn ):
setattr( newfn, '__doc__', fn.__doc__ )
return newfn
_loggers = lg.info, lg.output, lg.warn, lg.error, lg.debug
_loggers = tuple( makeListCompatible( logger )
for logger in _loggers )
+5 -1
View File
@@ -1,8 +1,11 @@
"Module dependency utility functions for Mininet."
from os import environ
from sys import exit # pylint: disable=redefined-builtin
from mininet.util import quietRun, BaseString
from mininet.log import info, error, debug
from os import environ
def lsmod():
"Return output of lsmod."
@@ -18,6 +21,7 @@ def modprobe( mod ):
mod: module string"""
return quietRun( [ 'modprobe', mod ] )
OF_KMOD = 'ofdatapath'
OVS_KMOD = 'openvswitch_mod' # Renamed 'openvswitch' in OVS 1.7+/Linux 3.5+
TUN = 'tun'
+2
View File
@@ -92,6 +92,7 @@ import select
import signal
import random
from sys import exit # pylint: disable=redefined-builtin
from time import sleep
from itertools import chain, groupby
from math import ceil
@@ -113,6 +114,7 @@ VERSION = "2.3.0a1"
class Mininet( object ):
"Network emulation with hosts spawned in network namespaces."
# pylint: disable=too-many-arguments
def __init__( self, topo=None, switch=OVSKernelSwitch, host=Host,
controller=DefaultController, link=Link, intf=Intf,
build=True, xterms=False, cleanup=False, ipBase='10.0.0.0/8',
+34 -14
View File
@@ -57,7 +57,10 @@ import pty
import re
import signal
import select
from distutils.version import StrictVersion
from re import findall
from subprocess import Popen, PIPE
from sys import exit # pylint: disable=redefined-builtin
from time import sleep
from mininet.log import info, error, warn, debug
@@ -66,8 +69,10 @@ from mininet.util import ( quietRun, errRun, errFail, moveIntf, isShellBuiltin,
encode, getincrementaldecoder, Python3, which )
from mininet.moduledeps import moduleDeps, pathCheck, TUN
from mininet.link import Link, Intf, TCIntf, OVSIntf
from re import findall
from distutils.version import StrictVersion
# pylint: disable=too-many-arguments
class Node( object ):
"""A virtual network node is simply a shell in a network namespace.
@@ -94,9 +99,13 @@ class Node( object ):
# Stash configuration parameters for future reference
self.params = params
self.intfs = {} # dict of port numbers to interfaces
self.ports = {} # dict of interfaces to port numbers
# replace with Port objects, eventually ?
# dict of port numbers to interfacse
self.intfs = {}
# dict of interfaces to port numbers
# todo: replace with Port objects, eventually ?
self.ports = {}
self.nameToIntf = {} # dict of interface names to Intfs
# Make pylint happy
@@ -284,6 +293,7 @@ class Node( object ):
returns: result of poll()"""
if len( self.readbuf ) == 0:
return self.pollOut.poll( timeoutms )
return None
def sendCmd( self, *args, **kwargs ):
"""Send a command, followed by a command to echo a sentinel,
@@ -377,6 +387,7 @@ class Node( object ):
return self.waitOutput( verbose )
else:
warn( '(%s exited - ignoring cmd%s)\n' % ( self, args ) )
return None
def cmdPrint( self, *args):
"""Call cmd and printing its output
@@ -469,6 +480,7 @@ class Node( object ):
else:
warn( '*** defaultIntf: warning:', self.name,
'has no interfaces\n' )
return None
def intf( self, intf=None ):
"""Return our interface object with given string name,
@@ -582,10 +594,10 @@ class Node( object ):
value may also be list or dict"""
name, value = list( param.items() )[ 0 ]
if value is None:
return
return None
f = getattr( self, method, None )
if not f:
return
return None
if isinstance( value, list ):
result = f( *value )
elif isinstance( value, dict ):
@@ -653,11 +665,12 @@ class Node( object ):
@classmethod
def checkSetup( cls ):
"Make sure our class and superclasses are set up"
while cls and not getattr( cls, 'isSetup', True ):
cls.setup()
cls.isSetup = True
clas = cls
while clas and not getattr( clas, 'isSetup', True ):
clas.setup()
clas.isSetup = True
# Make pylint happy
cls = getattr( type( cls ), '__base__', None )
clas = getattr( type( clas ), '__base__', None )
@classmethod
def setup( cls ):
@@ -838,6 +851,7 @@ class CPULimitedHost( Host ):
errFail( 'cgclassify -g cpuset:/%s %s' % (
self.name, self.pid ) )
# pylint: disable=arguments-differ
def config( self, cpu=-1, cores=None, **params ):
"""cpu: desired overall system CPU fraction
cores: (real) core(s) this host can run on
@@ -930,6 +944,7 @@ class Switch( Node ):
else:
error( '*** Error: %s has execed and cannot accept commands' %
self.name )
return None
def connected( self ):
"Is the switch connected to a controller? (override this method)"
@@ -1115,6 +1130,7 @@ class OVSSwitch( Switch ):
if self.batch:
cmd = ' '.join( str( arg ).strip() for arg in args )
self.commands.append( cmd )
return None
else:
return self.cmd( 'ovs-vsctl', *args, **kwargs )
@@ -1302,7 +1318,7 @@ class OVSBridge( OVSSwitch ):
"Are we forwarding yet?"
if self.stp:
status = self.dpctl( 'show' )
return 'STP_FORWARD' in status and not 'STP_LEARN' in status
return 'STP_FORWARD' in status and 'STP_LEARN' not in status
else:
return True
@@ -1429,6 +1445,7 @@ class Controller( Node ):
' 1>' + cout + ' 2>' + cout + ' &' )
self.execed = False
# pylint: disable=arguments-differ,signature-differs
def stop( self, *args, **kwargs ):
"Stop controller."
self.cmd( 'kill %' + self.command )
@@ -1479,7 +1496,7 @@ class NOX( Controller ):
warn( 'warning: no NOX modules specified; '
'running packetdump only\n' )
noxArgs = [ 'packetdump' ]
elif type( noxArgs ) not in ( list, tuple ):
elif not isinstance( noxArgs, ( list, tuple ) ):
noxArgs = [ noxArgs ]
if 'NOX_CORE_DIR' not in os.environ:
@@ -1505,7 +1522,7 @@ class Ryu( Controller ):
warn( 'warning: no Ryu modules specified; '
'running simple_switch only\n' )
ryuArgs = [ ryuCoreDir + 'simple_switch.py' ]
elif type( ryuArgs ) not in ( list, tuple ):
elif not isinstance( ryuArgs, ( list, tuple ) ):
ryuArgs = [ ryuArgs ]
Controller.__init__( self, name,
@@ -1532,6 +1549,7 @@ class RemoteController( Controller ):
"Overridden to do nothing."
return
# pylint: disable=arguments-differ
def stop( self ):
"Overridden to do nothing."
return
@@ -1563,6 +1581,7 @@ class RemoteController( Controller ):
else:
return True
DefaultControllers = ( Controller, OVSController )
def findController( controllers=DefaultControllers ):
@@ -1570,6 +1589,7 @@ def findController( controllers=DefaultControllers ):
for controller in controllers:
if controller.isAvailable():
return controller
return None
def DefaultController( name, controllers=DefaultControllers, **kwargs ):
"Find a controller that is available and instantiate it"
+1
View File
@@ -102,6 +102,7 @@ class NAT( Node ):
# hopefully this won't disconnect you
self.cmd( 'service network-manager restart || netplan apply' )
# pylint: disable=arguments-differ
def config( self, **params ):
"""Configure the NAT and iptables"""
+1 -1
View File
@@ -50,7 +50,7 @@ def makeTerm( node, title='Node', term='xterm', display=None, cmd='bash'):
}
if term not in cmds:
error( 'invalid terminal type: %s' % term )
return
return None
display, tunnel = tunnelX11( node, display )
if display is None:
return []
+1
View File
@@ -25,6 +25,7 @@ def runTests( testDir, verbosity=1 ):
.run( testSuite ).wasSuccessful() )
sys.exit( 0 if success else 1 )
if __name__ == '__main__':
setLogLevel( 'warning' )
# get the directory containing example tests
+2 -1
View File
@@ -45,7 +45,7 @@ class testOptionsTopoCommon( object ):
@staticmethod
def tearDown():
"Clean up if necessary"
if sys.exc_info != ( None, None, None ):
if sys.exc_info() != ( None, None, None ):
cleanup()
def runOptionsTopoTest( self, n, msg, hopts=None, lopts=None ):
@@ -263,6 +263,7 @@ class testOptionsTopoUserspace( testOptionsTopoCommon, unittest.TestCase ):
longMessage = True
switchClass = UserSwitch
if __name__ == '__main__':
setLogLevel( 'warning' )
unittest.main()
+1 -1
View File
@@ -26,7 +26,7 @@ class testSingleSwitchCommon( object ):
@staticmethod
def tearDown():
"Clean up if necessary"
if sys.exc_info != ( None, None, None ):
if sys.exc_info() != ( None, None, None ):
cleanup()
def testMinimal( self ):
+1
View File
@@ -26,6 +26,7 @@ class TestPtyLeak( unittest.TestCase ):
assert ( host.slave, host.master ) == oldptys
net.stop()
if __name__ == '__main__':
unittest.main()
cleanup()
+2 -1
View File
@@ -24,7 +24,7 @@ class TestSwitchDpidAssignmentOVS( unittest.TestCase ):
"Clean up if necessary"
# satisfy pylint
assert self
if sys.exc_info != ( None, None, None ):
if sys.exc_info() != ( None, None, None ):
cleanup()
def testDefaultDpid( self ):
@@ -95,6 +95,7 @@ class testSwitchUserspace( TestSwitchDpidAssignmentOVS ):
"Test dpid assignment of Userspace switch."
switchClass = UserSwitch
if __name__ == '__main__':
setLogLevel( 'warning' )
unittest.main()
+1
View File
@@ -35,5 +35,6 @@ class testQuietRun( unittest.TestCase ):
output = quietRun(testQuietRun.getEchoCmd( n ) )
self.assertEqual( n, len( output ) )
if __name__ == "__main__":
unittest.main()
+9 -7
View File
@@ -6,14 +6,16 @@ Tests for the Mininet Walkthrough
TODO: missing xterm test
"""
import unittest
import os
import re
from mininet.util import quietRun, pexpect
from mininet.clean import cleanup
import unittest
from distutils.version import StrictVersion
from sys import stdout
from mininet.util import quietRun, pexpect
from mininet.clean import cleanup
def tsharkVersion():
"Return tshark version"
@@ -74,7 +76,7 @@ class testWalkthrough( unittest.TestCase ):
p.expect( self.prompt )
# net command
p.sendline( 'net' )
expected = [ x for x in nodes ]
expected = list( nodes )
while len( expected ) > 0:
index = p.expect( expected )
node = p.match.group( 0 )
@@ -110,7 +112,7 @@ class testWalkthrough( unittest.TestCase ):
ifcount = 0
while True:
index = p.expect( interfaces )
if index == 0 or index == 3:
if index in (0, 3):
ifcount += 1
elif index == 1:
self.fail( 's1 interface displayed in "h1 ifconfig"' )
@@ -126,7 +128,7 @@ class testWalkthrough( unittest.TestCase ):
index = p.expect( interfaces )
if index == 0:
self.fail( 'h1 interface displayed in "s1 ifconfig"' )
elif index == 1 or index == 2 or index == 3:
elif index in (1, 2, 3):
ifcount += 1
else:
break
@@ -309,7 +311,7 @@ class testWalkthrough( unittest.TestCase ):
ifcount = 0
while True:
index = p.expect( interfaces )
if index == 1 or index == 3:
if index in (1, 3):
ifcount += 1
elif index == 0:
self.fail( 'h1 interface displayed in "s1 ifconfig"' )
+3
View File
@@ -13,6 +13,9 @@ setup for testing, and can even be emulated with the Mininet package.
from mininet.util import irange, natural, naturalSeq
# pylint: disable=too-many-arguments
class MultiGraph( object ):
"Utility class to track nodes and edges - replaces networkx.MultiGraph"
+15 -11
View File
@@ -1,19 +1,23 @@
"Utility functions for Mininet."
import codecs
import os
import re
import sys
from mininet.log import output, info, error, warn, debug
from time import sleep
from fcntl import fcntl, F_GETFL, F_SETFL
from functools import partial
from os import O_NONBLOCK
from resource import getrlimit, setrlimit, RLIMIT_NPROC, RLIMIT_NOFILE
from select import poll, POLLIN, POLLHUP
from subprocess import call, check_call, Popen, PIPE, STDOUT
import re
from fcntl import fcntl, F_GETFL, F_SETFL
from os import O_NONBLOCK
import os
from functools import partial
import sys
import codecs
from sys import exit # pylint: disable=redefined-builtin
from time import sleep
from mininet.log import output, info, error, warn, debug
# pylint: disable=too-many-arguments
# Python 2/3 compatibility
@@ -454,6 +458,7 @@ def pmonitor(popens, timeoutms=500, readline=True,
poller.register( fd, POLLIN )
flags = fcntl( fd, F_GETFL )
fcntl( fd, F_SETFL, flags | O_NONBLOCK )
# pylint: disable=too-many-nested-blocks
while popens:
fds = poller.poll( timeoutms )
if fds:
@@ -665,7 +670,6 @@ def ensureRoot():
if os.getuid() != 0:
error( '*** Mininet must run as root.\n' )
exit( 1 )
return
def waitListening( client=None, server='127.0.0.1', port=80, timeout=None ):
"""Wait until server is listening on port.