169 lines
4.2 KiB
Python
Executable file
169 lines
4.2 KiB
Python
Executable file
#!/usr/bin/env python
|
|
#
|
|
# Parses the CSV version of the IANA Service Name and Transport Protocol Port Number Registry
|
|
# and generates a services(5) file.
|
|
#
|
|
# Wireshark - Network traffic analyzer
|
|
# By Gerald Combs <gerald@wireshark.org>
|
|
# Copyright 2013 Gerald Combs
|
|
#
|
|
# This program is free software; you can redistribute it and/or
|
|
# modify it under the terms of the GNU General Public License
|
|
# as published by the Free Software Foundation; either version 2
|
|
# of the License, or (at your option) any later version.
|
|
#
|
|
# This program is distributed in the hope that it will be useful,
|
|
# but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
# GNU General Public License for more details.
|
|
#
|
|
# You should have received a copy of the GNU General Public License
|
|
# along with this program; if not, write to the Free Software
|
|
# Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
|
|
|
|
iana_svc_url = 'http://www.iana.org/assignments/service-names-port-numbers/service-names-port-numbers.csv'
|
|
|
|
__doc__ = '''\
|
|
Usage: make-services.py [url]
|
|
|
|
url defaults to
|
|
%s
|
|
''' % (iana_svc_url)
|
|
|
|
import sys
|
|
import getopt
|
|
import csv
|
|
import re
|
|
|
|
python_version = sys.hexversion >> 16
|
|
if python_version < 0x300:
|
|
import urllib
|
|
else:
|
|
import urllib.request, urllib.error, urllib.parse
|
|
import codecs
|
|
|
|
services_file = 'services'
|
|
|
|
exclude_services = [
|
|
'^spr-itunes',
|
|
'^spl-itunes',
|
|
'^shilp',
|
|
]
|
|
|
|
exclude_comments = [
|
|
'should not be used for discovery purposes',
|
|
'NOTE Conflict',
|
|
]
|
|
|
|
min_body_size = 900000 # Size was ~ 922000 on 2013-08-06
|
|
|
|
def parse_rows(svc_fd):
|
|
lines = []
|
|
port_reader = csv.reader(svc_fd)
|
|
|
|
# Header positions as of 2013-08-06
|
|
if python_version < 0x206:
|
|
headers = port_reader.next()
|
|
else:
|
|
headers = next(port_reader)
|
|
|
|
try:
|
|
sn_pos = headers.index('Service Name')
|
|
except:
|
|
sn_pos = 0
|
|
try:
|
|
pn_pos = headers.index('Port Number')
|
|
except:
|
|
pn_pos = 1
|
|
try:
|
|
tp_pos = headers.index('Transport Protocol')
|
|
except:
|
|
tp_pos = 2
|
|
|
|
positions = [sn_pos, pn_pos, tp_pos]
|
|
positions.sort()
|
|
positions.reverse()
|
|
|
|
for row in port_reader:
|
|
service = row[sn_pos]
|
|
port = row[pn_pos]
|
|
proto = row[tp_pos]
|
|
|
|
if len(service) < 1 or len(port) < 1 or len(proto) < 1:
|
|
continue
|
|
|
|
for pos in positions:
|
|
del row[pos]
|
|
row = filter(None, row)
|
|
comment = ' '.join(row)
|
|
comment = re.sub('[\n]', '', comment)
|
|
|
|
if re.search('|'.join(exclude_services), service):
|
|
continue
|
|
if re.search('|'.join(exclude_comments), comment):
|
|
continue
|
|
|
|
lines.append('%-15s %5s/%s # %s' % (
|
|
service,
|
|
port,
|
|
proto,
|
|
comment
|
|
))
|
|
|
|
return '\n'.join(lines)
|
|
|
|
def exit_msg(msg=None, status=1):
|
|
if msg is not None:
|
|
sys.stderr.write(msg + '\n')
|
|
sys.stderr.write(__doc__ + '\n')
|
|
sys.exit(1)
|
|
|
|
def main(argv):
|
|
try:
|
|
opts, args = getopt.getopt(argv, "h", ["help"])
|
|
except getopt.GetoptError:
|
|
exit_msg()
|
|
for opt, arg in opts:
|
|
if opt in ("-h", "--help"):
|
|
exit_msg(None, 0)
|
|
|
|
if (len(argv) > 0):
|
|
svc_url = argv[0]
|
|
else:
|
|
svc_url = iana_svc_url
|
|
|
|
try:
|
|
if python_version < 0x300:
|
|
svc_fd = urllib.urlopen(svc_url)
|
|
else:
|
|
req = urllib.request.urlopen(svc_url)
|
|
svc_fd = codecs.getreader('utf8')(req)
|
|
except URLError:
|
|
exit_err(URLError)
|
|
|
|
body = parse_rows(svc_fd)
|
|
if len(body) < min_body_size:
|
|
exit_err('Not enough parsed data')
|
|
|
|
out = open(services_file, 'w')
|
|
out.write('''\
|
|
# This is a local copy of the IANA port-numbers file.
|
|
#
|
|
# $Id$
|
|
#
|
|
# Wireshark uses it to resolve port numbers into human readable
|
|
# service names, e.g. TCP port 80 -> http.
|
|
#
|
|
# It is subject to copyright and being used with IANA's permission:
|
|
# http://www.wireshark.org/lists/wireshark-dev/200708/msg00160.html
|
|
#
|
|
# The original file can be found at:
|
|
# %s
|
|
#
|
|
|
|
%s
|
|
''' % (iana_svc_url, body))
|
|
|
|
if __name__ == "__main__":
|
|
sys.exit(main(sys.argv[1:]))
|