1 | #! /usr/bin/env python
|
---|
2 |
|
---|
3 | # 3) System Test
|
---|
4 | #
|
---|
5 | # Given a list of directories, report any bogus symbolic links contained
|
---|
6 | # anywhere in those subtrees. A bogus symbolic link is one that cannot
|
---|
7 | # be resolved because it points to a nonexistent or otherwise
|
---|
8 | # unresolvable file. Do *not* use an external find executable.
|
---|
9 | # Directories may be very very deep. Print a warning immediately if the
|
---|
10 | # system you're running on doesn't support symbolic links.
|
---|
11 |
|
---|
12 | # This implementation:
|
---|
13 | # - takes one optional argument, using the current directory as default
|
---|
14 | # - uses chdir to increase performance
|
---|
15 | # - sorts the names per directory
|
---|
16 | # - prints output lines of the form "path1 -> path2" as it goes
|
---|
17 | # - prints error messages about directories it can't list or chdir into
|
---|
18 |
|
---|
19 | import os
|
---|
20 | import sys
|
---|
21 | from stat import *
|
---|
22 |
|
---|
23 | def main():
|
---|
24 | try:
|
---|
25 | # Note: can't test for presence of lstat -- it's always there
|
---|
26 | dummy = os.readlink
|
---|
27 | except AttributeError:
|
---|
28 | print "This system doesn't have symbolic links"
|
---|
29 | sys.exit(0)
|
---|
30 | if sys.argv[1:]:
|
---|
31 | prefix = sys.argv[1]
|
---|
32 | else:
|
---|
33 | prefix = ''
|
---|
34 | if prefix:
|
---|
35 | os.chdir(prefix)
|
---|
36 | if prefix[-1:] != '/': prefix = prefix + '/'
|
---|
37 | reportboguslinks(prefix)
|
---|
38 | else:
|
---|
39 | reportboguslinks('')
|
---|
40 |
|
---|
41 | def reportboguslinks(prefix):
|
---|
42 | try:
|
---|
43 | names = os.listdir('.')
|
---|
44 | except os.error, msg:
|
---|
45 | print "%s%s: can't list: %s" % (prefix, '.', msg)
|
---|
46 | return
|
---|
47 | names.sort()
|
---|
48 | for name in names:
|
---|
49 | if name == os.curdir or name == os.pardir:
|
---|
50 | continue
|
---|
51 | try:
|
---|
52 | mode = os.lstat(name)[ST_MODE]
|
---|
53 | except os.error:
|
---|
54 | print "%s%s: can't stat: %s" % (prefix, name, msg)
|
---|
55 | continue
|
---|
56 | if S_ISLNK(mode):
|
---|
57 | try:
|
---|
58 | os.stat(name)
|
---|
59 | except os.error:
|
---|
60 | print "%s%s -> %s" % \
|
---|
61 | (prefix, name, os.readlink(name))
|
---|
62 | elif S_ISDIR(mode):
|
---|
63 | try:
|
---|
64 | os.chdir(name)
|
---|
65 | except os.error, msg:
|
---|
66 | print "%s%s: can't chdir: %s" % \
|
---|
67 | (prefix, name, msg)
|
---|
68 | continue
|
---|
69 | try:
|
---|
70 | reportboguslinks(prefix + name + '/')
|
---|
71 | finally:
|
---|
72 | os.chdir('..')
|
---|
73 |
|
---|
74 | main()
|
---|