Minor cleanup; clarified fdToNode (still need to test however.)

This commit is contained in:
Bob Lantz
2010-02-08 15:51:43 -08:00
parent d5886525cc
commit 6d72a3cb0c
+41 -40
View File
@@ -1,11 +1,11 @@
"""
Node objects for Mininet.
Nodes provide a simple abstraction for interacting with
hosts, switches and controllers. Local nodes are simply
one or more processes on the local machine.
Nodes provide a simple abstraction for interacting with hosts, switches
and controllers. Local nodes are simply one or more processes on the local
machine.
Node: superclass for all (currently only local) network nodes.
Node: superclass for all (primarily local) network nodes.
Host: a virtual host.
@@ -33,20 +33,18 @@ RemoteController: a remote controller node, which may use any
from subprocess import Popen, PIPE, STDOUT
import os
import signal
import sys
import select
flush = sys.stdout.flush
from mininet.log import lg
from mininet.log import info, error
from mininet.util import quietRun, macColonHex, ipStr
class Node( object ):
"""A virtual network node is simply a shell in a network namespace.
We communicate with it using pipes."""
inToNode = {}
outToNode = {}
inToNode = {} # mapping of input fds to nodes
outToNode = {} # mapping of output fds to nodes
def __init__( self, name, inNamespace=True ):
self.name = name
@@ -71,28 +69,29 @@ class Node( object ):
self.intfCount = 0
self.intfs = [] # list of interface names, as strings
self.ips = {} # dict of interfaces to ip addresses as strings
self.connection = {}
self.connection = {} # remote node connected to each interface
self.waiting = False
self.execed = False
self.ports = {} # dict of ints to interface strings
# replace with Port object, eventually
def fdToNode( self, f ):
"""Insert docstring.
f: unknown
returns: bool unknown"""
node = self.outToNode.get( f )
return node or self.inToNode.get( f )
@classmethod
def fdToNode( cls, fd ):
"""Return node corresponding to given file descriptor.
fd: file descriptor
returns: node"""
node = Node.outToNode.get( fd )
return node or Node.inToNode.get( fd )
def cleanup( self ):
"Help python collect its garbage."
self.shell = None
# Subshell I/O, commands and control
def read( self, filenoMax ):
"""Insert docstring.
filenoMax: unknown"""
return os.read( self.stdout.fileno(), filenoMax )
def read( self, bytes ):
"""Read from a node.
bytes: maximum number of bytes to read"""
return os.read( self.stdout.fileno(), bytes )
def write( self, data ):
"""Write data to node.
@@ -100,7 +99,7 @@ class Node( object ):
os.write( self.stdin.fileno(), data )
def terminate( self ):
"Send kill signal to Node and cleanup after it."
"Send kill signal to Node and clean up after it."
os.kill( self.pid, signal.SIGKILL )
self.cleanup()
@@ -109,7 +108,7 @@ class Node( object ):
self.terminate()
def waitReadable( self ):
"Poll on node."
"Wait until node's output is readable."
self.pollOut.poll()
def sendCmd( self, cmd ):
@@ -127,7 +126,7 @@ class Node( object ):
self.waiting = True
def monitor( self ):
"Monitor the output of a command, returning (done, data)."
"Monitor the output of a command, returning (done?, data)."
assert self.waiting
self.waitReadable()
data = self.read( 1024 )
@@ -138,7 +137,7 @@ class Node( object ):
return False, data
def sendInt( self ):
"Send ^C, hopefully interrupting a running subprocess."
"Send ^C, hopefully interrupting an interactive subprocess."
self.write( chr( 3 ) )
def waitOutput( self ):
@@ -168,9 +167,9 @@ class Node( object ):
def cmdPrint( self, cmd ):
"""Call cmd and printing its output
cmd: string"""
#lg.info( '*** %s : %s', self.name, cmd )
#info( '*** %s : %s', self.name, cmd )
result = self.cmd( cmd )
#lg.info( '%s\n', result )
#info( '%s\n', result )
return result
# Interface management, configuration, and routing
@@ -249,7 +248,7 @@ class Host( Node ):
class Switch( Node ):
"""A Switch is a Node that is running ( or has execed )
"""A Switch is a Node that is running (or has execed?)
an OpenFlow switch."""
def sendCmd( self, cmd ):
@@ -258,7 +257,7 @@ class Switch( Node ):
if not self.execed:
return Node.sendCmd( self, cmd )
else:
lg.error( '*** Error: %s has execed and cannot accept commands' %
error( '*** Error: %s has execed and cannot accept commands' %
self.name )
def monitor( self ):
@@ -280,7 +279,7 @@ class UserSwitch( Switch ):
def start( self, controllers ):
"""Start OpenFlow reference user datapath.
Log to /tmp/sN-{ ofd,ofp }.log.
Log to /tmp/sN-{ofd,ofp}.log.
controllers: dict of controller names to objects"""
if 'c0' not in controllers:
raise Exception( 'User datapath start() requires controller c0' )
@@ -289,11 +288,13 @@ class UserSwitch( Switch ):
ofplog = '/tmp/' + self.name + '-ofp.log'
self.cmd( 'ifconfig lo up' )
intfs = self.intfs
self.cmdPrint( 'ofdatapath -i ' + ','.join( intfs ) + ' punix:/tmp/' +
self.name + ' 1> ' + ofdlog + ' 2> ' + ofdlog + ' &' )
self.cmdPrint( 'ofprotocol unix:/tmp/' + self.name + ' tcp:' +
controller.IP() + ' --fail=closed 1> ' + ofplog + ' 2>' +
ofplog + ' &' )
self.cmdPrint( 'ofdatapath -i ' + ','.join( intfs ) +
' punix:/tmp/' + self.name +
' 1> ' + ofdlog + ' 2> ' + ofdlog + ' &' )
self.cmdPrint( 'ofprotocol unix:/tmp/' + self.name +
' tcp:' + controller.IP() + ' --fail=closed' +
' 1> ' + ofplog + ' 2>' + ofplog + ' &' )
def stop( self ):
"Stop OpenFlow reference user datapath."
@@ -308,7 +309,7 @@ class KernelSwitch( Switch ):
def __init__( self, name, dp=None, dpid=None ):
"""Init.
name:
dp: netlink id ( 0, 1, 2, ... )
dp: netlink id (0, 1, 2, ...)
dpid: datapath ID as unsigned int; random value if None"""
Switch.__init__( self, name, inNamespace=False )
self.dp = dp
@@ -350,7 +351,7 @@ class KernelSwitch( Switch ):
self.cmd( 'kill %ofprotocol' )
for intf in self.intfs:
quietRun( 'ip link del ' + intf )
lg.info( '.' )
info( '.' )
class OVSKernelSwitch( Switch ):
@@ -360,7 +361,7 @@ class OVSKernelSwitch( Switch ):
def __init__( self, name, dp=None, dpid=None ):
"""Init.
name:
dp: netlink id ( 0, 1, 2, ... )
dp: netlink id (0, 1, 2, ...)
dpid: datapath ID as unsigned int; random value if None"""
Switch.__init__( self, name, inNamespace=False )
self.dp = dp
@@ -401,7 +402,7 @@ class OVSKernelSwitch( Switch ):
self.cmd( 'kill %ovs-openflowd' )
for intf in self.intfs:
quietRun( 'ip link del ' + intf )
lg.info( '.' )
info( '.' )
class Controller( Node ):
@@ -465,7 +466,7 @@ class NOX( Controller ):
raise Exception( 'please set NOX_CORE_DIR env var\n' )
Controller.__init__( self, name,
controller=noxCoreDir + '/nox_core',
cargs='--libdir=/usr/local/lib -v -i ptcp: ' + \
cargs='--libdir=/usr/local/lib -v -i ptcp: ' +
' '.join( noxArgs ),
cdir = noxCoreDir, **kwargs )