aboutsummaryrefslogtreecommitdiffstats
path: root/english/security/oval/oval/parser/dsa.py
blob: 1ec9fb3b6d5ed9111338d5de04884c9f34c6dd86 (plain) (blame)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
# -*- coding: utf-8 -*-
# oval.parser.dsa - module to parse Debian Security Advisories files.
#
# Extrected tags:
# 	<pagetitle>
#		<report_date>
#		<secrefs>
#		<packages>
#		<isvulnerable>
#		<fixed>
#
# (c) 2007 Pavel Vinogradov     
# (c) 2004 Javier Fernandez-Sanguino                                                                                                  
# Licensed under the GNU General Public License version 2.

import re
import os
import logging

# Format of data files is:
#<define-tag pagetitle>DSA-###-# PACKAGE</define-tag>                                                                                          
#<define-tag report_date>yyyy-mm-dd</define-tag>                                                                                               
#<define-tag secrefs>CAN|CVE-XXXX-XXXX</define-tag>                                                                                            
#<define-tag packages>PACKAGE</define-tag>                                                                                                     
#<define-tag isvulnerable>yes|no</define-tag>                                                                                                  
#<define-tag fixed>yes|no</define-tag>  
def parseFile (path):
	""" Parse data file with information of Debian Security Advisories 
	
	Keyword arguments:
	path -- full path to data file
	
	return list (dsa id, tags and packages data)"""
	

	data = {}
	deb_ver = None
	fdeb_ver = None
	
	filename = os.path.basename (path)

	patern = re.compile(r'dsa-(\d+)')
	result = patern.search(filename)
	if result:
		dsa = result.groups()[0]
	else:
		logging.log(logging.WARNING, "File %s does not look like a proper DSA, not checking" % filename)
		return (None)

	logging.log (logging.DEBUG, "Parsing DSA %s from file %s" % (dsa, filename))

	dsaFile = open(path)
	
	for line in dsaFile:
		line= line.decode ("ISO-8859-2")
		datepatern = re.compile (r'report_date>([\d-]+)</define-tag>')
		result = datepatern.search (line)
		if result:
			date = result.groups()[0]
			normDate = lambda (date): "-".join([(len(p) > 1 and p or "0"+p) for p in date.split("-")])
			data["date"] = normDate(date)
		
		descrpatern = re.compile (r'(CVE-\d+-\d+)')
		result = descrpatern.search (line)
		if result:
			data["description"] = result.groups()[0]
			logging.log(logging.DEBUG, "Extracted CVE ID: " + data["description"])
			continue
		
		refspatern = re.compile (r'secrefs>(.*?)</define-tag>')
		result = refspatern.search (line)
		if result:
			data["secrefs"] = result.groups()[0]
			logging.log(logging.DEBUG, "Extracted security references: " + data["secrefs"])

		pakpatern = re.compile (r'packages>(.*?)</define-tag>')
		result = pakpatern.search (line)
		if result:
			data["packages"] = result.groups()[0]

		vulpatern = re.compile (r'isvulnerable>(.*?)</define-tag>')
		result = vulpatern.search (line)
		if result:
			data["vulnarable"] = result.groups()[0]

		fixpatern = re.compile (r'fixed>(.*?)</define-tag>')
		result = fixpatern.search (line)
		if result:
			data["fixed"] = result.groups()[0]

		versionpatern = re.compile (r'<h3>Debian GNU/Linux (\d.\d) \((.*?)\)</h3>')
		result = versionpatern.search (line)
		if result:
			fdeb_ver = result.groups()[0]

                # Alternative format for data files
		versionpatern = re.compile (r'affected_release>([\d\.]+)<')
		result = versionpatern.search (line)
		if result:
			fdeb_ver = result.groups()[0]
			
                if fdeb_ver:
                        deb_ver = fdeb_ver 
                        fdeb_ver = None
			if data.has_key("release"):
				if data["release"].has_key(deb_ver):
					logging.log(logging.WARNING, "DSA %s: Found second files section for release %s" % (dsa, deb_ver))
				else:
					data["release"][deb_ver] = {}
			else:
				data["release"] = {deb_ver: {}}

		# Binary packages are pushed into array
		# Those are prepended by fileurls
		# TODO: Packages do _NOT_ include epochs 
		# (that should be fixed)
		if data.has_key("release") and deb_ver:
			urlpatern = re.compile (r'fileurl [\w:/.\-+]+/([\w\-.+~]+)\.deb[^i]')
			result = urlpatern.search (line)
			if result:
				(package, version, architecture) = result.groups()[0].split("_")
					
				if data["release"][deb_ver].has_key(architecture):
					data["release"][deb_ver][architecture][package] = version
				else:
					data["release"][deb_ver][architecture] = {package : version}
	
	return (dsa, data)

© 2014-2024 Faster IT GmbH | imprint | privacy policy