blob: 4510374dd1f7503a3e3443e8cbc8e8bb3ec024ee [file] [log] [blame]
#!/usr/bin/python
import urllib2
import json
import re
import sys
from optparse import OptionParser
sys.path.append('~/floodlight/target/gen-py')
sys.path.append('~/floodlight/thrift/lib/py')
from packetstreamer import PacketStreamer
from packetstreamer.ttypes import *
from thrift import Thrift
from thrift.transport import TSocket
from thrift.transport import TTransport
from thrift.protocol import TBinaryProtocol
SESSIONID = 'sessionId'
usage = "usage: %prog [options]"
parser = OptionParser(usage=usage, version="%prog 1.0")
parser.add_option("-c", "--controller", dest="controller", metavar="CONTROLLER_IP",
default="127.0.0.1", help="controller's IP address")
parser.add_option("-m", "--mac", dest="mac", metavar="HOST_MAC",
help="The host mac address to trace the OF packets")
(options, args) = parser.parse_args()
def validateIp(ip):
ipReg = ("(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)"
"\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)"
"\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)"
"\.(25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)")
m = re.compile(ipReg).match(ip)
if m:
return True
else :
return False
def validateMac(mac):
macReg = '([a-fA-F0-9]{2}:){5}[a-fA-F0-9]{2}' # same regex as above
m = re.compile(macReg).match(mac)
if m:
return True
else :
return False
if not validateIp(options.controller):
parser.error("Invalid format for ip address.")
if not options.mac:
parser.error("-m or --mac option is required.")
if not validateMac(options.mac):
parser.error("Invalid format for mac address. Format: xx:xx:xx:xx:xx:xx")
controller = options.controller
host = options.mac
url = 'http://%s:8080/wm/core/packettrace/json' % controller
filter = {'mac':host, 'direction':'both', 'period':1000}
post_data = json.dumps(filter)
request = urllib2.Request(url, post_data, {'Content-Type':'application/json'})
response_text = None
def terminateTrace(sid):
global controller
filter = {SESSIONID:sid, 'period':-1}
post_data = json.dumps(filter)
url = 'http://%s:8080/wm/core/packettrace/json' % controller
request = urllib2.Request(url, post_data, {'Content-Type':'application/json'})
try:
response = urllib2.urlopen(request)
response_text = response.read()
except Exception, e:
# Floodlight may not be running, but we don't want that to be a fatal
# error, so we just ignore the exception in that case.
print "Exception:", e
try:
response = urllib2.urlopen(request)
response_text = response.read()
except Exception, e:
# Floodlight may not be running, but we don't want that to be a fatal
# error, so we just ignore the exception in that case.
print "Exception:", e
exit
if not response_text:
print "Failed to start a packet trace session"
sys.exit()
response_text = json.loads(response_text)
sessionId = None
if SESSIONID in response_text:
sessionId = response_text[SESSIONID]
else:
print "Failed to start a packet trace session"
sys.exit()
try:
# Make socket
transport = TSocket.TSocket('localhost', 9090)
# Buffering is critical. Raw sockets are very slow
transport = TTransport.TFramedTransport(transport)
# Wrap in a protocol
protocol = TBinaryProtocol.TBinaryProtocol(transport)
# Create a client to use the protocol encoder
client = PacketStreamer.Client(protocol)
# Connect!
transport.open()
while 1:
packets = client.getPackets(sessionId)
for packet in packets:
print "Packet: %s"% packet
if "FilterTimeout" in packet:
sys.exit()
except Thrift.TException, e:
print '%s' % (e.message)
terminateTrace(sessionId)
except KeyboardInterrupt, e:
terminateTrace(sessionId)
# Close!
transport.close()