1
1
# Support for scanning init scripts for LSB info
5
FACILITIES = '/var/lib/lsb/facilities'
3
import re, sys, os, cStringIO
11
class RFC822Parser(dict):
12
"A dictionary-like object."
13
__linere = re.compile(r'([^:]+):\s*(.*)$')
15
def __init__(self, fileob=None, strob=None, startcol=0, basedict=None):
16
if not fileob and not strob:
17
raise ValueError, 'need a file or string'
21
super(RFC822Parser, self).__init__(basedict)
24
fileob = cStringIO.StringIO(strob)
29
line = line[startcol:]
38
self[key] += '\n' + line.strip()
41
m = self.__linere.match(line)
43
# Not a valid RFC822 header
45
key, value = m.groups()
46
self[key] = value.strip()
50
LSBLIB = '/var/lib/lsb'
51
FACILITIES = os.path.join(LSBLIB, 'facilities')
52
DEPENDS = os.path.join(LSBLIB, 'depends')
7
54
beginre = re.compile(re.escape('### BEGIN INIT INFO'))
8
55
endre = re.compile(re.escape('### END INIT INFO'))
9
linere = re.compile(r'\#\s+([^:]+):\s*(.*)')
56
#linere = re.compile(r'\#\s+([^:]+):\s*(.*)')
11
58
def scan_initfile(initfile):
12
headers = {'Description': []}
15
for line in open(initfile).xreadlines():
62
for line in file(initfile):
16
63
line = line.rstrip()
17
64
if beginre.match(line):
20
67
elif scanning and endre.match(line):
29
if line[1:3] == ' ' or line[1] == '\t':
30
headers['Description'].append(line[1:].strip())
33
match = linere.match(line)
35
print >> sys.stderr, "Warning: ignoring invalid init info line"
36
print >> sys.stderr, "-> %s" % line
39
header, body = match.groups()
40
if header == "Description":
41
headers[header].append(body.strip())
42
elif header in ('Default-Start', 'Default-Stop'):
73
if line.startswith('# '):
74
headerlines += line[2:] + '\n'
75
elif line.startswith('#\t'):
76
headerlines += line[1:] + '\n'
78
inheaders = RFC822Parser(strob=headerlines)
80
for header, body in inheaders.iteritems():
81
if header in ('Default-Start', 'Default-Stop'):
43
82
headers[header] = map(int, body.split())
44
elif header in ('Required-Start', 'Required-Stop', 'Provides'):
83
elif header in ('Required-Start', 'Required-Stop', 'Provides',
84
'Should-Start', 'Should-Stop'):
45
85
headers[header] = body.split()
47
87
headers[header] = body
59
items = facilities.items()
60
fh = open(FACILITIES, 'w')
61
for facility, entries in items:
62
if facility[0] == '$': continue
63
for scriptname, pri in entries.items():
99
fh = file(FACILITIES, 'w')
100
for facility, entries in facilities.items():
101
# Ignore system facilities
102
if facility.startswith('$'): continue
103
for (scriptname, pri) in entries.items():
65
105
print >> fh, "%(scriptname)s %(facility)s %(start)d %(stop)d" % locals()
71
111
for line in open(FACILITIES).xreadlines():
73
113
scriptname, name, start, stop = line.strip().split()
74
facilities.get(name, {})[scriptname] = (int(start), int(stop))
114
facilities.setdefault(name, {})[scriptname] = (int(start),
75
116
except ValueError, x:
76
117
print >> sys.stderr, 'Invalid facility line', line
124
if os.path.exists(DEPENDS):
125
independs = RFC822Parser(fileob=file(DEPENDS))
126
for initfile, facilities in independs.iteritems():
127
depends[initfile] = facilities.split()
130
def save_depends(depends):
138
fh = file(DEPENDS, 'w')
139
for initfile, facilities in depends.iteritems():
140
print >> fh, '%s: %s' % (initfile, ' '.join(facilities))
143
if __name__ == '__main__':
144
print scan_initfile('init-fragment')