Preliminary support for systemd. Checkrestart now looks for service files and, if the system
is running systemd, it will suggest to use systemctl instead of 'service' to restart those
packages that require it.
Javier Fernandez-Sanguino
9 years ago
58 | 58 | return location |
59 | 59 | return 1 |
60 | 60 | |
61 | def checksystemd(): | |
62 | # Check if systemd is installed in the system | |
63 | if os.path.exists('/bin/systemd'): | |
64 | return 0 | |
65 | return 1 | |
66 | ||
61 | 67 | def usage(): |
62 | 68 | sys.stderr.write('usage: checkrestart [-vhpa] [-bblacklist] [-iignore]\n') |
63 | 69 | |
69 | 75 | lc_all_c_env = os.environ |
70 | 76 | lc_all_c_env['LC_ALL'] = 'C' |
71 | 77 | file_query_check = {} |
78 | is_systemd = False | |
72 | 79 | blacklistFiles = [] |
73 | 80 | blacklist = [] |
74 | ignorelist = [ 'screen' ] | |
81 | ignorelist = [ 'screen', 'systemd' ] | |
75 | 82 | |
76 | 83 | # Process options |
77 | 84 | try: |
119 | 126 | |
120 | 127 | # Start checking |
121 | 128 | |
129 | if checksystemd() == 0: | |
130 | is_systemd = True | |
131 | ||
122 | 132 | if find_cmd('lsof') == 1: |
123 | 133 | sys.stderr.write('ERROR: This program needs lsof in order to run.\n') |
124 | 134 | sys.stderr.write('Please install the lsof package in your system.\n') |
147 | 157 | else: |
148 | 158 | print "(%d distinct programs)" % len(programs) |
149 | 159 | |
150 | # Verbose information | |
160 | #services Verbose information | |
151 | 161 | if verbose: |
152 | 162 | for process in toRestart: |
153 | 163 | print "Process %s (PID: %d) " % (process.program, process.pid) |
224 | 234 | if path.endswith('.sh'): |
225 | 235 | continue |
226 | 236 | package.initscripts.add(path[12:]) |
237 | # If running on a systemd system, extract the systemd's service files from the package | |
238 | if is_systemd and path.startswith('/lib/systemd/system/') and path.endswith('.service') and path.find('.wants') == -1: | |
239 | # Read the service file and make sure it is not of type 'oneshot' | |
240 | servicefile = open (path) | |
241 | is_oneshot = False | |
242 | for line in servicefile.readlines (): | |
243 | if line.find ('Type=oneshot') > 0: | |
244 | is_oneshot = True | |
245 | continue | |
246 | servicefile.close () | |
247 | if not is_oneshot: | |
248 | package.systemdservice.add(path[20:]) | |
227 | 249 | sys.stdout.flush() |
228 | 250 | dpkgProc.stdout.close() |
229 | 251 | |
230 | 252 | # Alternatively, find init.d scripts that match the process name |
231 | if len(package.initscripts) == 0: | |
253 | if len(package.initscripts) == 0 and len(package.systemdservice) == 0: | |
232 | 254 | for process in package.processes: |
233 | 255 | proc_name = os.path.basename(process.program) |
234 | 256 | if os.path.exists('/etc/init.d/' + proc_name): |
236 | 258 | |
237 | 259 | restartable = [] |
238 | 260 | nonrestartable = [] |
239 | restartCommands = [] | |
261 | restartInitCommands = [] | |
262 | restartServiceCommands = [] | |
240 | 263 | for package in packages.values(): |
241 | 264 | if len(package.initscripts) > 0: |
242 | 265 | restartable.append(package) |
243 | restartCommands.extend(map(lambda s: 'service ' + s + ' restart',package.initscripts)) | |
266 | restartInitCommands.extend(map(lambda s: 'service ' + s + ' restart', package.initscripts)) | |
267 | elif len(package.systemdservice) > 0: | |
268 | restartable.append(package) | |
269 | restartServiceCommands.extend(map(lambda s: 'systemctl restart ' + s, package.systemdservice)) | |
244 | 270 | else: |
245 | 271 | nonrestartable.append(package) |
246 | 272 | |
247 | 273 | if len(restartable) > 0: |
248 | 274 | |
249 | print "Of these, %d seem to contain init scripts which can be used to restart them:" % len(restartable) | |
275 | print "Of these, %d seem to contain systemd service definitions or init scripts which can be used to restart them." % len(restartable) | |
250 | 276 | # TODO - consider putting this in a --verbose option |
251 | print "The following packages seem to have init scripts that could be used\nto restart them:" | |
277 | print "The following packages seem to have definitions that could be used\nto restart their services:" | |
252 | 278 | for package in restartable: |
253 | 279 | print package.name + ':' |
254 | 280 | for process in package.processes: |
255 | 281 | print "\t%s\t%s" % (process.pid,process.program) |
256 | 282 | |
257 | ||
258 | print "These are the init scripts:" | |
259 | print '\n'.join(restartCommands) | |
260 | ||
283 | if len(restartServiceCommands)>0: | |
284 | ||
285 | print "These are the systemd services:" | |
286 | print '\n'.join(restartServiceCommands) | |
287 | ||
288 | ||
289 | if len(restartInitCommands)>0: | |
290 | print "These are the initd scripts:" | |
291 | print '\n'.join(restartInitCommands) | |
292 | ||
261 | 293 | |
262 | 294 | if len(nonrestartable) == 0: |
263 | 295 | sys.exit(0) |
264 | 296 | |
265 | 297 | # TODO - consider putting this in a --verbose option |
266 | print "These processes do not seem to have an associated init script to restart them:" | |
298 | print "These processes (%d) do not seem to have an associated init script to restart them:" %len(nonrestartable) | |
267 | 299 | for package in nonrestartable: |
268 | 300 | skip = False |
269 | 301 | if ignorelist: |
633 | 665 | self.name = name |
634 | 666 | # use a set, we don't need duplicates |
635 | 667 | self.initscripts = set() |
668 | self.systemdservice = set() | |
636 | 669 | self.processes = [] |
637 | 670 | |
638 | 671 | if __name__ == '__main__': |