summaryrefslogtreecommitdiffstats
path: root/scripts/automation/trex_control_plane/stl/services/scapy_server/scapy_service.py
diff options
context:
space:
mode:
authoritraviv <itraviv@cisco.com>2016-08-15 17:52:38 +0300
committeritraviv <itraviv@cisco.com>2016-08-15 17:52:38 +0300
commit2c575880c6b5bd0a6c4f1df91f819118af800699 (patch)
treeea751687ef67f7452d31d6510d7a065df0146fe2 /scripts/automation/trex_control_plane/stl/services/scapy_server/scapy_service.py
parent72171290152897fac1a149fe4f9d1cbf0ae914c4 (diff)
scapy_server_test:
added cases for testing: GRE, VXML, DNS, IPv6 changed test functions to include only the testted object and created other functions as testing engines. scapy_service: added api class. added documentry for api class changed method functions to include underscore
Diffstat (limited to 'scripts/automation/trex_control_plane/stl/services/scapy_server/scapy_service.py')
-rwxr-xr-xscripts/automation/trex_control_plane/stl/services/scapy_server/scapy_service.py214
1 files changed, 145 insertions, 69 deletions
diff --git a/scripts/automation/trex_control_plane/stl/services/scapy_server/scapy_service.py b/scripts/automation/trex_control_plane/stl/services/scapy_server/scapy_service.py
index 638d35f2..3519bb58 100755
--- a/scripts/automation/trex_control_plane/stl/services/scapy_server/scapy_service.py
+++ b/scripts/automation/trex_control_plane/stl/services/scapy_server/scapy_service.py
@@ -2,7 +2,9 @@
import os
import sys
stl_pathname = os.path.abspath(os.path.join(os.pardir, os.pardir))
+additional_stl_udp_pkts = os.path.abspath(os.path.join(os.pardir, os.pardir,'stl'))
sys.path.append(stl_pathname)
+sys.path.append(additional_stl_udp_pkts)
import trex_stl_lib
from trex_stl_lib.api import *
from copy import deepcopy
@@ -11,32 +13,106 @@ import tempfile
import hashlib
import binascii
from pprint import pprint
-
+from scapy.layers.dns import *
+from udp_1pkt_vxlan import VXLAN
+from udp_1pkt_mpls import MPLS
try:
from cStringIO import StringIO
except ImportError:
from io import StringIO
-"""
- **** output redirection template ****
-old_stdout = sys.stdout
-sys.stdout = mystdout = StringIO()
-ls()
-sys.stdout = old_stdout
-a= mystdout.getvalue()
+class Scapy_service_api():
+ """ get_all(self)
-f = open('scapy_supported_formats.txt','w')
-f.write(a)
-f.close()
-"""
+ Sends all the protocols and fields that Scapy Service supports.
+ also sends the md5 of the Protocol DB and Fields DB used to check if the DB's are up to date
-class ScapyException(Exception): pass
+ Parameters
+ ----------
+ None
+
+ Returns
+ -------
+ Dictionary (of protocol DB and scapy fields DB)
+
+ Raises
+ ------
+ Raises an exception when a DB error occurs (i.e a layer is not loaded properly and has missing components)
+ """
+ def get_all(self):
+ pass
+
+ """ check_update(self,db_md5,field_md5)
+ Checks if the Scapy Service running on the server has a newer version of the databases that the client has
+
+ Parameters
+ ----------
+ db_md5 - The md5 that was delivered with the protocol database that the client owns, when first received at the client
+ field_md5 - The md5 that was delivered with the fields database that the client owns, when first received at the client
+
+ Returns
+ -------
+ True/False according the Databases version(determined by their md5)
+
+ Raises
+ ------
+ Raises an exception (ScapyException) when protocol DB/Fields DB is not up to date
+
+ """
-class Scapy_service:
+ def check_update(self,db_md5,field_md5):
+ pass
+
+ """ build_pkt(self,pkt_descriptor) -> Dictionary (of Offsets,Show2 and Buffer)
+
+ Performs calculations on the given packet and returns results for that packet.
+
+ Parameters
+ ----------
+ pkt_descriptor - A string describing a network packet, in Scapy Format
+
+ Returns
+ -------
+ - The packets offsets: each field in every layer is mapped inside the Offsets Dictionary
+ - The Show2: A description of each field and its value in every layer of the packet
+ - The Buffer: The Hexdump of packet encoded in base64
+
+ Raises
+ ------
+ will raise an exception when the Scapy string format is illegal, contains syntax error, contains non-supported
+ protocl, etc.
+ """
+ def build_pkt(self,pkt_descriptor):
+ pass
+
+ """ get_tree(self) -> Dictionary describing an example of hierarchy in layers
+
+ Scapy service holds a tree of layers that can be stacked to a recommended packet
+ according to the hierarchy
+
+ Parameters
+ ----------
+ None
+
+ Returns
+ -------
+ Returns an example hierarchy tree of layers that can be stacked to a packet
+
+ Raises
+ ------
+ None
+ """
+ def get_tree(self):
+ pass
+
+
+
+class ScapyException(Exception): pass
+class Scapy_service(Scapy_service_api):
#----------------------------------------------------------------------------------------------------
class scapyRegex:
@@ -55,10 +131,10 @@ class Scapy_service:
self.low_level_protocols = { 'Ether': self.network_protocols }
self.regexDB= {'MACField' : self.scapyRegex('MACField','^([0-9a-fA-F][0-9a-fA-F]:){5}([0-9a-fA-F][0-9a-fA-F])$'),
'IPField' : self.scapyRegex('IPField','^(25[0-5]|2[0-4][0-9]|[0-1]{1}[0-9]{2}|[1-9]{1}[0-9]{1}|[1-9])\.(25[0-5]|2[0-4][0-9]|[0-1]{1}[0-9]{2}|[1-9]{1}[0-9]{1}|[1-9]|0)\.(25[0-5]|2[0-4][0-9]|[0-1]{1}[0-9]{2}|[1-9]{1}[0-9]{1}|[1-9]|0)\.(25[0-5]|2[0-4][0-9]|[0-1]{1}[0-9]{2}|[1-9]{1}[0-9]{1}|[0-9])$')}
- self.all_protocols = self.build_lib()
+ self.all_protocols = self._build_lib()
self.protocol_tree = {'ALL':{'Ether':{'ARP':{},'IP':{'TCP':{'RAW':'payload'},'UDP':{'RAW':'payload'}}}}}
- def protocol_struct(self,protocol=''):
+ def _protocol_struct(self,protocol=''):
if '_' in protocol:
return []
if not protocol=='':
@@ -75,8 +151,8 @@ class Scapy_service:
protocol_data= mystdout.getvalue()
return protocol_data
- def build_lib(self):
- lib = self.protocol_struct()
+ def _build_lib(self):
+ lib = self._protocol_struct()
lib = lib.split('\n')
all_protocols=[]
for entry in lib:
@@ -85,45 +161,39 @@ class Scapy_service:
del all_protocols[len(all_protocols)-1]
return all_protocols
- def parse_description_line(self,line):
+ def _parse_description_line(self,line):
line_arr = [x.strip() for x in re.split(': | = ',line)]
return tuple(line_arr)
- def parse_entire_description(self,description):
+ def _parse_entire_description(self,description):
description = description.split('\n')
- description_list = [self.parse_description_line(x) for x in description]
+ description_list = [self._parse_description_line(x) for x in description]
del description_list[len(description_list)-1]
return description_list
- def get_protocol_details(self,p_name):
- protocol_str = self.protocol_struct(p_name)
+ def _get_protocol_details(self,p_name):
+ protocol_str = self._protocol_struct(p_name)
if protocol_str=='protocol not supported':
return 'protocol not supported'
if len(protocol_str) is 0:
return []
- tupled_protocol = self.parse_entire_description(protocol_str)
+ tupled_protocol = self._parse_entire_description(protocol_str)
return tupled_protocol
- def print_tree(self):
+ def _print_tree(self):
pprint(self.protocol_tree)
- def get_all_protocols(self):
- return self.all_protocols
-
- def get_tree(self):
- return self.protocol_tree
-
- def get_all_db(self):
+ def _get_all_db(self):
db = {}
for pro in self.all_protocols:
- details = self.get_protocol_details(pro)
+ details = self._get_protocol_details(pro)
db[pro] = details
return db
- def get_all_fields(self):
+ def _get_all_fields(self):
fields = []
for pro in self.all_protocols:
- details = self.get_protocol_details(pro)
+ details = self._get_protocol_details(pro)
for i in range(0,len(details),1):
if len(details[i]) is 3:
fields.append(details[i][1])
@@ -136,7 +206,7 @@ class Scapy_service:
fieldDict[f] = self.scapyRegex(f).stringRegex()
return fieldDict
- def show2_to_dict(self,pkt):
+ def _show2_to_dict(self,pkt):
old_stdout = sys.stdout
sys.stdout = mystdout = StringIO()
pkt.show2()
@@ -160,7 +230,7 @@ class Scapy_service:
#pkt_desc as string
#dictionary of offsets per protocol. tuple for each field: (name, offset, size) at json format
- def get_all_pkt_offsets(self,pkt_desc):
+ def _get_all_pkt_offsets(self,pkt_desc):
pkt_protocols = pkt_desc.split('/')
scapy_pkt = eval(pkt_desc)
scapy_pkt.build()
@@ -181,34 +251,51 @@ class Scapy_service:
scapy_pkt=scapy_pkt.payload
return res
-# pkt_descriptor in string format
+#input: container
+#output: md5 encoded in base64
+ def _get_md5(self,container):
+ container = json.dumps(container)
+ m = hashlib.md5()
+ m.update(container.encode('ascii'))
+ res_md5 = binascii.b2a_base64(m.digest())
+ return res_md5
+ def get_version(self):
+ return {'built_by':'itraviv','version':'v1.0'}
+
+ def supported_methods(self,method_name=''):
+ if method_name=='':
+ methods = {}
+ for f in dir(Scapy_service):
+ if inspect.ismethod(eval('Scapy_service.'+f)):
+ methods[f] = inspect.getargspec(eval('Scapy_service.'+f))[0]
+ return methods
+ if method_name in dir(Scapy_service):
+ return True
+ return False
+
+#--------------------------------------------API implementation-------------
+ def get_tree(self):
+ return self.protocol_tree
+
+# pkt_descriptor in string format
def build_pkt(self,pkt_descriptor):
pkt = eval(pkt_descriptor)
- show2data = self.show2_to_dict(pkt)
+ show2data = self._show2_to_dict(pkt)
bufferData = str(pkt) #pkt buffer
bufferData = binascii.b2a_base64(bufferData)
- pkt_offsets = self.get_all_pkt_offsets(pkt_descriptor)
+ pkt_offsets = self._get_all_pkt_offsets(pkt_descriptor)
res = {}
res['show2'] = show2data
res['buffer'] = bufferData
res['offsets'] = pkt_offsets
return res
-#input: container
-#output: md5 encoded in base64
- def get_md5(self,container):
- container = json.dumps(container)
- m = hashlib.md5()
- m.update(container.encode('ascii'))
- res_md5 = binascii.b2a_base64(m.digest())
- return res_md5
-
def get_all(self):
- fields=self.get_all_fields()
- db=self.get_all_db()
- fields_md5 = self.get_md5(fields)
- db_md5 = self.get_md5(db)
+ fields=self._get_all_fields()
+ db=self._get_all_db()
+ fields_md5 = self._get_md5(fields)
+ db_md5 = self._get_md5(db)
res = {}
res['db'] = db
res['fields'] = fields
@@ -218,10 +305,10 @@ class Scapy_service:
#input in string encoded base64
def check_update(self,db_md5,field_md5):
- fields=self.get_all_fields()
- db=self.get_all_db()
- current_db_md5 = self.get_md5(db)
- current_field_md5 = self.get_md5(fields)
+ fields=self._get_all_fields()
+ db=self._get_all_db()
+ current_db_md5 = self._get_md5(db)
+ current_field_md5 = self._get_md5(fields)
res = []
if (field_md5.decode("base64") == current_field_md5.decode("base64")):
if (db_md5.decode("base64") == current_db_md5.decode("base64")):
@@ -231,18 +318,7 @@ class Scapy_service:
else:
raise ScapyException("Fields DB is not up to date")
- def get_version(self):
- return {'built_by':'itraviv','version':'v1.0'}
- def supported_methods(self,method_name=''):
- if method_name=='':
- methods = {}
- for f in dir(Scapy_service):
- if inspect.ismethod(eval('Scapy_service.'+f)):
- methods[f] = inspect.getargspec(eval('Scapy_service.'+f))[0]
- return methods
- if method_name in dir(Scapy_service):
- return True
- return False
+#---------------------------------------------------------------------------