diff options
| author | Linus Torvalds <torvalds@linux-foundation.org> | 2016-10-03 22:57:49 -0400 |
|---|---|---|
| committer | Linus Torvalds <torvalds@linux-foundation.org> | 2016-10-03 22:57:49 -0400 |
| commit | 7a53eea1f7b527fd3b6d7ca992914840981afe99 (patch) | |
| tree | 35dfd7e14d5c44ae2d34e470aaaa68dbfec39324 /scripts | |
| parent | 597f03f9d133e9837d00965016170271d4f87dcf (diff) | |
| parent | c9fef1cc3dd3677633e6fd6ea5bd7ef3b741fab3 (diff) | |
Merge tag 'char-misc-4.9-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc
Pull char/misc driver updates from Greg KH:
"Here's the "big" char and misc driver update for 4.9-rc1.
Lots of little things here, all over the driver tree for subsystems
that flow through me. Nothing major that I can discern, full details
are in the shortlog.
All have been in the linux-next tree with no reported issues"
* tag 'char-misc-4.9-rc1' of git://git.kernel.org/pub/scm/linux/kernel/git/gregkh/char-misc: (144 commits)
drivers/misc/hpilo: Changes to support new security states in iLO5 FW
at25: fix debug and error messaging
misc/genwqe: ensure zero initialization
vme: fake: remove unexpected unlock in fake_master_set()
vme: fake: mark symbols static where possible
spmi: pmic-arb: Return an error code if sanity check fails
Drivers: hv: get rid of id in struct vmbus_channel
Drivers: hv: make VMBus bus ids persistent
mcb: Add a dma_device to mcb_device
mcb: Enable PCI bus mastering by default
mei: stop the stall timer worker if not needed
clk: probe common clock drivers earlier
vme: fake: fix build for 64-bit dma_addr_t
ttyprintk: Neaten and simplify printing
mei: me: add kaby point device ids
coresight: tmc: mark symbols static where possible
coresight: perf: deal with error condition properly
Drivers: hv: hv_util: Avoid dynamic allocation in time synch
fpga manager: Add hardware dependency to Zynq driver
Drivers: hv: utils: Support TimeSync version 4.0 protocol samples.
...
Diffstat (limited to 'scripts')
| -rwxr-xr-x | scripts/checkkconfigsymbols.py | 338 | ||||
| -rwxr-xr-x | scripts/ver_linux | 260 |
2 files changed, 252 insertions, 346 deletions
diff --git a/scripts/checkkconfigsymbols.py b/scripts/checkkconfigsymbols.py index df643f60bb41..a32e4da4c117 100755 --- a/scripts/checkkconfigsymbols.py +++ b/scripts/checkkconfigsymbols.py | |||
| @@ -1,98 +1,99 @@ | |||
| 1 | #!/usr/bin/env python2 | 1 | #!/usr/bin/env python3 |
| 2 | 2 | ||
| 3 | """Find Kconfig symbols that are referenced but not defined.""" | 3 | """Find Kconfig symbols that are referenced but not defined.""" |
| 4 | 4 | ||
| 5 | # (c) 2014-2015 Valentin Rothberg <valentinrothberg@gmail.com> | 5 | # (c) 2014-2016 Valentin Rothberg <valentinrothberg@gmail.com> |
| 6 | # (c) 2014 Stefan Hengelein <stefan.hengelein@fau.de> | 6 | # (c) 2014 Stefan Hengelein <stefan.hengelein@fau.de> |
| 7 | # | 7 | # |
| 8 | # Licensed under the terms of the GNU GPL License version 2 | 8 | # Licensed under the terms of the GNU GPL License version 2 |
| 9 | 9 | ||
| 10 | 10 | ||
| 11 | import argparse | ||
| 11 | import difflib | 12 | import difflib |
| 12 | import os | 13 | import os |
| 13 | import re | 14 | import re |
| 14 | import signal | 15 | import signal |
| 16 | import subprocess | ||
| 15 | import sys | 17 | import sys |
| 16 | from multiprocessing import Pool, cpu_count | 18 | from multiprocessing import Pool, cpu_count |
| 17 | from optparse import OptionParser | ||
| 18 | from subprocess import Popen, PIPE, STDOUT | ||
| 19 | 19 | ||
| 20 | 20 | ||
| 21 | # regex expressions | 21 | # regex expressions |
| 22 | OPERATORS = r"&|\(|\)|\||\!" | 22 | OPERATORS = r"&|\(|\)|\||\!" |
| 23 | FEATURE = r"(?:\w*[A-Z0-9]\w*){2,}" | 23 | SYMBOL = r"(?:\w*[A-Z0-9]\w*){2,}" |
| 24 | DEF = r"^\s*(?:menu){,1}config\s+(" + FEATURE + r")\s*" | 24 | DEF = r"^\s*(?:menu){,1}config\s+(" + SYMBOL + r")\s*" |
| 25 | EXPR = r"(?:" + OPERATORS + r"|\s|" + FEATURE + r")+" | 25 | EXPR = r"(?:" + OPERATORS + r"|\s|" + SYMBOL + r")+" |
| 26 | DEFAULT = r"default\s+.*?(?:if\s.+){,1}" | 26 | DEFAULT = r"default\s+.*?(?:if\s.+){,1}" |
| 27 | STMT = r"^\s*(?:if|select|depends\s+on|(?:" + DEFAULT + r"))\s+" + EXPR | 27 | STMT = r"^\s*(?:if|select|depends\s+on|(?:" + DEFAULT + r"))\s+" + EXPR |
| 28 | SOURCE_FEATURE = r"(?:\W|\b)+[D]{,1}CONFIG_(" + FEATURE + r")" | 28 | SOURCE_SYMBOL = r"(?:\W|\b)+[D]{,1}CONFIG_(" + SYMBOL + r")" |
| 29 | 29 | ||
| 30 | # regex objects | 30 | # regex objects |
| 31 | REGEX_FILE_KCONFIG = re.compile(r".*Kconfig[\.\w+\-]*$") | 31 | REGEX_FILE_KCONFIG = re.compile(r".*Kconfig[\.\w+\-]*$") |
| 32 | REGEX_FEATURE = re.compile(r'(?!\B)' + FEATURE + r'(?!\B)') | 32 | REGEX_SYMBOL = re.compile(r'(?!\B)' + SYMBOL + r'(?!\B)') |
| 33 | REGEX_SOURCE_FEATURE = re.compile(SOURCE_FEATURE) | 33 | REGEX_SOURCE_SYMBOL = re.compile(SOURCE_SYMBOL) |
| 34 | REGEX_KCONFIG_DEF = re.compile(DEF) | 34 | REGEX_KCONFIG_DEF = re.compile(DEF) |
| 35 | REGEX_KCONFIG_EXPR = re.compile(EXPR) | 35 | REGEX_KCONFIG_EXPR = re.compile(EXPR) |
| 36 | REGEX_KCONFIG_STMT = re.compile(STMT) | 36 | REGEX_KCONFIG_STMT = re.compile(STMT) |
| 37 | REGEX_KCONFIG_HELP = re.compile(r"^\s+(help|---help---)\s*$") | 37 | REGEX_KCONFIG_HELP = re.compile(r"^\s+(help|---help---)\s*$") |
| 38 | REGEX_FILTER_FEATURES = re.compile(r"[A-Za-z0-9]$") | 38 | REGEX_FILTER_SYMBOLS = re.compile(r"[A-Za-z0-9]$") |
| 39 | REGEX_NUMERIC = re.compile(r"0[xX][0-9a-fA-F]+|[0-9]+") | 39 | REGEX_NUMERIC = re.compile(r"0[xX][0-9a-fA-F]+|[0-9]+") |
| 40 | REGEX_QUOTES = re.compile("(\"(.*?)\")") | 40 | REGEX_QUOTES = re.compile("(\"(.*?)\")") |
| 41 | 41 | ||
| 42 | 42 | ||
| 43 | def parse_options(): | 43 | def parse_options(): |
| 44 | """The user interface of this module.""" | 44 | """The user interface of this module.""" |
| 45 | usage = "%prog [options]\n\n" \ | 45 | usage = "Run this tool to detect Kconfig symbols that are referenced but " \ |
| 46 | "Run this tool to detect Kconfig symbols that are referenced but " \ | 46 | "not defined in Kconfig. If no option is specified, " \ |
| 47 | "not defined in\nKconfig. The output of this tool has the " \ | 47 | "checkkconfigsymbols defaults to check your current tree. " \ |
| 48 | "format \'Undefined symbol\\tFile list\'\n\n" \ | 48 | "Please note that specifying commits will 'git reset --hard\' " \ |
| 49 | "If no option is specified, %prog will default to check your\n" \ | 49 | "your current tree! You may save uncommitted changes to avoid " \ |
| 50 | "current tree. Please note that specifying commits will " \ | 50 | "losing data." |
| 51 | "\'git reset --hard\'\nyour current tree! You may save " \ | 51 | |
| 52 | "uncommitted changes to avoid losing data." | 52 | parser = argparse.ArgumentParser(description=usage) |
| 53 | 53 | ||
| 54 | parser = OptionParser(usage=usage) | 54 | parser.add_argument('-c', '--commit', dest='commit', action='store', |
| 55 | 55 | default="", | |
| 56 | parser.add_option('-c', '--commit', dest='commit', action='store', | 56 | help="check if the specified commit (hash) introduces " |
| 57 | default="", | 57 | "undefined Kconfig symbols") |
| 58 | help="Check if the specified commit (hash) introduces " | 58 | |
| 59 | "undefined Kconfig symbols.") | 59 | parser.add_argument('-d', '--diff', dest='diff', action='store', |
| 60 | 60 | default="", | |
| 61 | parser.add_option('-d', '--diff', dest='diff', action='store', | 61 | help="diff undefined symbols between two commits " |
| 62 | default="", | 62 | "(e.g., -d commmit1..commit2)") |
| 63 | help="Diff undefined symbols between two commits. The " | 63 | |
| 64 | "input format bases on Git log's " | 64 | parser.add_argument('-f', '--find', dest='find', action='store_true', |
| 65 | "\'commmit1..commit2\'.") | 65 | default=False, |
| 66 | 66 | help="find and show commits that may cause symbols to be " | |
| 67 | parser.add_option('-f', '--find', dest='find', action='store_true', | 67 | "missing (required to run with --diff)") |
| 68 | default=False, | 68 | |
| 69 | help="Find and show commits that may cause symbols to be " | 69 | parser.add_argument('-i', '--ignore', dest='ignore', action='store', |
| 70 | "missing. Required to run with --diff.") | 70 | default="", |
| 71 | 71 | help="ignore files matching this Python regex " | |
| 72 | parser.add_option('-i', '--ignore', dest='ignore', action='store', | 72 | "(e.g., -i '.*defconfig')") |
| 73 | default="", | 73 | |
| 74 | help="Ignore files matching this pattern. Note that " | 74 | parser.add_argument('-s', '--sim', dest='sim', action='store', default="", |
| 75 | "the pattern needs to be a Python regex. To " | 75 | help="print a list of max. 10 string-similar symbols") |
| 76 | "ignore defconfigs, specify -i '.*defconfig'.") | 76 | |
| 77 | 77 | parser.add_argument('--force', dest='force', action='store_true', | |
| 78 | parser.add_option('-s', '--sim', dest='sim', action='store', default="", | 78 | default=False, |
| 79 | help="Print a list of maximum 10 string-similar symbols.") | 79 | help="reset current Git tree even when it's dirty") |
| 80 | 80 | ||
| 81 | parser.add_option('', '--force', dest='force', action='store_true', | 81 | parser.add_argument('--no-color', dest='color', action='store_false', |
| 82 | default=False, | 82 | default=True, |
| 83 | help="Reset current Git tree even when it's dirty.") | 83 | help="don't print colored output (default when not " |
| 84 | 84 | "outputting to a terminal)") | |
| 85 | (opts, _) = parser.parse_args() | 85 | |
| 86 | 86 | args = parser.parse_args() | |
| 87 | if opts.commit and opts.diff: | 87 | |
| 88 | if args.commit and args.diff: | ||
| 88 | sys.exit("Please specify only one option at once.") | 89 | sys.exit("Please specify only one option at once.") |
| 89 | 90 | ||
| 90 | if opts.diff and not re.match(r"^[\w\-\.]+\.\.[\w\-\.]+$", opts.diff): | 91 | if args.diff and not re.match(r"^[\w\-\.]+\.\.[\w\-\.]+$", args.diff): |
| 91 | sys.exit("Please specify valid input in the following format: " | 92 | sys.exit("Please specify valid input in the following format: " |
| 92 | "\'commit1..commit2\'") | 93 | "\'commit1..commit2\'") |
| 93 | 94 | ||
| 94 | if opts.commit or opts.diff: | 95 | if args.commit or args.diff: |
| 95 | if not opts.force and tree_is_dirty(): | 96 | if not args.force and tree_is_dirty(): |
| 96 | sys.exit("The current Git tree is dirty (see 'git status'). " | 97 | sys.exit("The current Git tree is dirty (see 'git status'). " |
| 97 | "Running this script may\ndelete important data since it " | 98 | "Running this script may\ndelete important data since it " |
| 98 | "calls 'git reset --hard' for some performance\nreasons. " | 99 | "calls 'git reset --hard' for some performance\nreasons. " |
| @@ -100,138 +101,148 @@ def parse_options(): | |||
| 100 | "'--force' if you\nwant to ignore this warning and " | 101 | "'--force' if you\nwant to ignore this warning and " |
| 101 | "continue.") | 102 | "continue.") |
| 102 | 103 | ||
| 103 | if opts.commit: | 104 | if args.commit: |
| 104 | opts.find = False | 105 | args.find = False |
| 105 | 106 | ||
| 106 | if opts.ignore: | 107 | if args.ignore: |
| 107 | try: | 108 | try: |
| 108 | re.match(opts.ignore, "this/is/just/a/test.c") | 109 | re.match(args.ignore, "this/is/just/a/test.c") |
| 109 | except: | 110 | except: |
| 110 | sys.exit("Please specify a valid Python regex.") | 111 | sys.exit("Please specify a valid Python regex.") |
| 111 | 112 | ||
| 112 | return opts | 113 | return args |
| 113 | 114 | ||
| 114 | 115 | ||
| 115 | def main(): | 116 | def main(): |
| 116 | """Main function of this module.""" | 117 | """Main function of this module.""" |
| 117 | opts = parse_options() | 118 | args = parse_options() |
| 118 | 119 | ||
| 119 | if opts.sim and not opts.commit and not opts.diff: | 120 | global COLOR |
| 120 | sims = find_sims(opts.sim, opts.ignore) | 121 | COLOR = args.color and sys.stdout.isatty() |
| 122 | |||
| 123 | if args.sim and not args.commit and not args.diff: | ||
| 124 | sims = find_sims(args.sim, args.ignore) | ||
| 121 | if sims: | 125 | if sims: |
| 122 | print "%s: %s" % (yel("Similar symbols"), ', '.join(sims)) | 126 | print("%s: %s" % (yel("Similar symbols"), ', '.join(sims))) |
| 123 | else: | 127 | else: |
| 124 | print "%s: no similar symbols found" % yel("Similar symbols") | 128 | print("%s: no similar symbols found" % yel("Similar symbols")) |
| 125 | sys.exit(0) | 129 | sys.exit(0) |
| 126 | 130 | ||
| 127 | # dictionary of (un)defined symbols | 131 | # dictionary of (un)defined symbols |
| 128 | defined = {} | 132 | defined = {} |
| 129 | undefined = {} | 133 | undefined = {} |
| 130 | 134 | ||
| 131 | if opts.commit or opts.diff: | 135 | if args.commit or args.diff: |
| 132 | head = get_head() | 136 | head = get_head() |
| 133 | 137 | ||
| 134 | # get commit range | 138 | # get commit range |
| 135 | commit_a = None | 139 | commit_a = None |
| 136 | commit_b = None | 140 | commit_b = None |
| 137 | if opts.commit: | 141 | if args.commit: |
| 138 | commit_a = opts.commit + "~" | 142 | commit_a = args.commit + "~" |
| 139 | commit_b = opts.commit | 143 | commit_b = args.commit |
| 140 | elif opts.diff: | 144 | elif args.diff: |
| 141 | split = opts.diff.split("..") | 145 | split = args.diff.split("..") |
| 142 | commit_a = split[0] | 146 | commit_a = split[0] |
| 143 | commit_b = split[1] | 147 | commit_b = split[1] |
| 144 | undefined_a = {} | 148 | undefined_a = {} |
| 145 | undefined_b = {} | 149 | undefined_b = {} |
| 146 | 150 | ||
| 147 | # get undefined items before the commit | 151 | # get undefined items before the commit |
| 148 | execute("git reset --hard %s" % commit_a) | 152 | reset(commit_a) |
| 149 | undefined_a, _ = check_symbols(opts.ignore) | 153 | undefined_a, _ = check_symbols(args.ignore) |
| 150 | 154 | ||
| 151 | # get undefined items for the commit | 155 | # get undefined items for the commit |
| 152 | execute("git reset --hard %s" % commit_b) | 156 | reset(commit_b) |
| 153 | undefined_b, defined = check_symbols(opts.ignore) | 157 | undefined_b, defined = check_symbols(args.ignore) |
| 154 | 158 | ||
| 155 | # report cases that are present for the commit but not before | 159 | # report cases that are present for the commit but not before |
| 156 | for feature in sorted(undefined_b): | 160 | for symbol in sorted(undefined_b): |
| 157 | # feature has not been undefined before | 161 | # symbol has not been undefined before |
| 158 | if not feature in undefined_a: | 162 | if symbol not in undefined_a: |
| 159 | files = sorted(undefined_b.get(feature)) | 163 | files = sorted(undefined_b.get(symbol)) |
| 160 | undefined[feature] = files | 164 | undefined[symbol] = files |
| 161 | # check if there are new files that reference the undefined feature | 165 | # check if there are new files that reference the undefined symbol |
| 162 | else: | 166 | else: |
| 163 | files = sorted(undefined_b.get(feature) - | 167 | files = sorted(undefined_b.get(symbol) - |
| 164 | undefined_a.get(feature)) | 168 | undefined_a.get(symbol)) |
| 165 | if files: | 169 | if files: |
| 166 | undefined[feature] = files | 170 | undefined[symbol] = files |
| 167 | 171 | ||
| 168 | # reset to head | 172 | # reset to head |
| 169 | execute("git reset --hard %s" % head) | 173 | reset(head) |
| 170 | 174 | ||
| 171 | # default to check the entire tree | 175 | # default to check the entire tree |
| 172 | else: | 176 | else: |
| 173 | undefined, defined = check_symbols(opts.ignore) | 177 | undefined, defined = check_symbols(args.ignore) |
| 174 | 178 | ||
| 175 | # now print the output | 179 | # now print the output |
| 176 | for feature in sorted(undefined): | 180 | for symbol in sorted(undefined): |
| 177 | print red(feature) | 181 | print(red(symbol)) |
| 178 | 182 | ||
| 179 | files = sorted(undefined.get(feature)) | 183 | files = sorted(undefined.get(symbol)) |
| 180 | print "%s: %s" % (yel("Referencing files"), ", ".join(files)) | 184 | print("%s: %s" % (yel("Referencing files"), ", ".join(files))) |
| 181 | 185 | ||
| 182 | sims = find_sims(feature, opts.ignore, defined) | 186 | sims = find_sims(symbol, args.ignore, defined) |
| 183 | sims_out = yel("Similar symbols") | 187 | sims_out = yel("Similar symbols") |
| 184 | if sims: | 188 | if sims: |
| 185 | print "%s: %s" % (sims_out, ', '.join(sims)) | 189 | print("%s: %s" % (sims_out, ', '.join(sims))) |
| 186 | else: | 190 | else: |
| 187 | print "%s: %s" % (sims_out, "no similar symbols found") | 191 | print("%s: %s" % (sims_out, "no similar symbols found")) |
| 188 | 192 | ||
| 189 | if opts.find: | 193 | if args.find: |
| 190 | print "%s:" % yel("Commits changing symbol") | 194 | print("%s:" % yel("Commits changing symbol")) |
| 191 | commits = find_commits(feature, opts.diff) | 195 | commits = find_commits(symbol, args.diff) |
| 192 | if commits: | 196 | if commits: |
| 193 | for commit in commits: | 197 | for commit in commits: |
| 194 | commit = commit.split(" ", 1) | 198 | commit = commit.split(" ", 1) |
| 195 | print "\t- %s (\"%s\")" % (yel(commit[0]), commit[1]) | 199 | print("\t- %s (\"%s\")" % (yel(commit[0]), commit[1])) |
| 196 | else: | 200 | else: |
| 197 | print "\t- no commit found" | 201 | print("\t- no commit found") |
| 198 | print # new line | 202 | print() # new line |
| 203 | |||
| 204 | |||
| 205 | def reset(commit): | ||
| 206 | """Reset current git tree to %commit.""" | ||
| 207 | execute(["git", "reset", "--hard", commit]) | ||
| 199 | 208 | ||
| 200 | 209 | ||
| 201 | def yel(string): | 210 | def yel(string): |
| 202 | """ | 211 | """ |
| 203 | Color %string yellow. | 212 | Color %string yellow. |
| 204 | """ | 213 | """ |
| 205 | return "\033[33m%s\033[0m" % string | 214 | return "\033[33m%s\033[0m" % string if COLOR else string |
| 206 | 215 | ||
| 207 | 216 | ||
| 208 | def red(string): | 217 | def red(string): |
| 209 | """ | 218 | """ |
| 210 | Color %string red. | 219 | Color %string red. |
| 211 | """ | 220 | """ |
| 212 | return "\033[31m%s\033[0m" % string | 221 | return "\033[31m%s\033[0m" % string if COLOR else string |
| 213 | 222 | ||
| 214 | 223 | ||
| 215 | def execute(cmd): | 224 | def execute(cmd): |
| 216 | """Execute %cmd and return stdout. Exit in case of error.""" | 225 | """Execute %cmd and return stdout. Exit in case of error.""" |
| 217 | pop = Popen(cmd, stdout=PIPE, stderr=STDOUT, shell=True) | 226 | try: |
| 218 | (stdout, _) = pop.communicate() # wait until finished | 227 | stdout = subprocess.check_output(cmd, stderr=subprocess.STDOUT, shell=False) |
| 219 | if pop.returncode != 0: | 228 | stdout = stdout.decode(errors='replace') |
| 220 | sys.exit(stdout) | 229 | except subprocess.CalledProcessError as fail: |
| 230 | exit(fail) | ||
| 221 | return stdout | 231 | return stdout |
| 222 | 232 | ||
| 223 | 233 | ||
| 224 | def find_commits(symbol, diff): | 234 | def find_commits(symbol, diff): |
| 225 | """Find commits changing %symbol in the given range of %diff.""" | 235 | """Find commits changing %symbol in the given range of %diff.""" |
| 226 | commits = execute("git log --pretty=oneline --abbrev-commit -G %s %s" | 236 | commits = execute(["git", "log", "--pretty=oneline", |
| 227 | % (symbol, diff)) | 237 | "--abbrev-commit", "-G", |
| 238 | symbol, diff]) | ||
| 228 | return [x for x in commits.split("\n") if x] | 239 | return [x for x in commits.split("\n") if x] |
| 229 | 240 | ||
| 230 | 241 | ||
| 231 | def tree_is_dirty(): | 242 | def tree_is_dirty(): |
| 232 | """Return true if the current working tree is dirty (i.e., if any file has | 243 | """Return true if the current working tree is dirty (i.e., if any file has |
| 233 | been added, deleted, modified, renamed or copied but not committed).""" | 244 | been added, deleted, modified, renamed or copied but not committed).""" |
| 234 | stdout = execute("git status --porcelain") | 245 | stdout = execute(["git", "status", "--porcelain"]) |
| 235 | for line in stdout: | 246 | for line in stdout: |
| 236 | if re.findall(r"[URMADC]{1}", line[:2]): | 247 | if re.findall(r"[URMADC]{1}", line[:2]): |
| 237 | return True | 248 | return True |
| @@ -240,13 +251,13 @@ def tree_is_dirty(): | |||
| 240 | 251 | ||
| 241 | def get_head(): | 252 | def get_head(): |
| 242 | """Return commit hash of current HEAD.""" | 253 | """Return commit hash of current HEAD.""" |
| 243 | stdout = execute("git rev-parse HEAD") | 254 | stdout = execute(["git", "rev-parse", "HEAD"]) |
| 244 | return stdout.strip('\n') | 255 | return stdout.strip('\n') |
| 245 | 256 | ||
| 246 | 257 | ||
| 247 | def partition(lst, size): | 258 | def partition(lst, size): |
| 248 | """Partition list @lst into eveni-sized lists of size @size.""" | 259 | """Partition list @lst into eveni-sized lists of size @size.""" |
| 249 | return [lst[i::size] for i in xrange(size)] | 260 | return [lst[i::size] for i in range(size)] |
| 250 | 261 | ||
| 251 | 262 | ||
| 252 | def init_worker(): | 263 | def init_worker(): |
| @@ -254,7 +265,7 @@ def init_worker(): | |||
| 254 | signal.signal(signal.SIGINT, signal.SIG_IGN) | 265 | signal.signal(signal.SIGINT, signal.SIG_IGN) |
| 255 | 266 | ||
| 256 | 267 | ||
| 257 | def find_sims(symbol, ignore, defined = []): | 268 | def find_sims(symbol, ignore, defined=[]): |
| 258 | """Return a list of max. ten Kconfig symbols that are string-similar to | 269 | """Return a list of max. ten Kconfig symbols that are string-similar to |
| 259 | @symbol.""" | 270 | @symbol.""" |
| 260 | if defined: | 271 | if defined: |
| @@ -279,7 +290,7 @@ def find_sims(symbol, ignore, defined = []): | |||
| 279 | def get_files(): | 290 | def get_files(): |
| 280 | """Return a list of all files in the current git directory.""" | 291 | """Return a list of all files in the current git directory.""" |
| 281 | # use 'git ls-files' to get the worklist | 292 | # use 'git ls-files' to get the worklist |
| 282 | stdout = execute("git ls-files") | 293 | stdout = execute(["git", "ls-files"]) |
| 283 | if len(stdout) > 0 and stdout[-1] == "\n": | 294 | if len(stdout) > 0 and stdout[-1] == "\n": |
| 284 | stdout = stdout[:-1] | 295 | stdout = stdout[:-1] |
| 285 | 296 | ||
| @@ -311,8 +322,8 @@ def check_symbols_helper(pool, ignore): | |||
| 311 | check_symbols() in order to properly terminate running worker processes.""" | 322 | check_symbols() in order to properly terminate running worker processes.""" |
| 312 | source_files = [] | 323 | source_files = [] |
| 313 | kconfig_files = [] | 324 | kconfig_files = [] |
| 314 | defined_features = [] | 325 | defined_symbols = [] |
| 315 | referenced_features = dict() # {file: [features]} | 326 | referenced_symbols = dict() # {file: [symbols]} |
| 316 | 327 | ||
| 317 | for gitfile in get_files(): | 328 | for gitfile in get_files(): |
| 318 | if REGEX_FILE_KCONFIG.match(gitfile): | 329 | if REGEX_FILE_KCONFIG.match(gitfile): |
| @@ -326,76 +337,75 @@ def check_symbols_helper(pool, ignore): | |||
| 326 | # parse source files | 337 | # parse source files |
| 327 | arglist = partition(source_files, cpu_count()) | 338 | arglist = partition(source_files, cpu_count()) |
| 328 | for res in pool.map(parse_source_files, arglist): | 339 | for res in pool.map(parse_source_files, arglist): |
| 329 | referenced_features.update(res) | 340 | referenced_symbols.update(res) |
| 330 | |||
| 331 | 341 | ||
| 332 | # parse kconfig files | 342 | # parse kconfig files |
| 333 | arglist = [] | 343 | arglist = [] |
| 334 | for part in partition(kconfig_files, cpu_count()): | 344 | for part in partition(kconfig_files, cpu_count()): |
| 335 | arglist.append((part, ignore)) | 345 | arglist.append((part, ignore)) |
| 336 | for res in pool.map(parse_kconfig_files, arglist): | 346 | for res in pool.map(parse_kconfig_files, arglist): |
| 337 | defined_features.extend(res[0]) | 347 | defined_symbols.extend(res[0]) |
| 338 | referenced_features.update(res[1]) | 348 | referenced_symbols.update(res[1]) |
| 339 | defined_features = set(defined_features) | 349 | defined_symbols = set(defined_symbols) |
| 340 | 350 | ||
| 341 | # inverse mapping of referenced_features to dict(feature: [files]) | 351 | # inverse mapping of referenced_symbols to dict(symbol: [files]) |
| 342 | inv_map = dict() | 352 | inv_map = dict() |
| 343 | for _file, features in referenced_features.iteritems(): | 353 | for _file, symbols in referenced_symbols.items(): |
| 344 | for feature in features: | 354 | for symbol in symbols: |
| 345 | inv_map[feature] = inv_map.get(feature, set()) | 355 | inv_map[symbol] = inv_map.get(symbol, set()) |
| 346 | inv_map[feature].add(_file) | 356 | inv_map[symbol].add(_file) |
| 347 | referenced_features = inv_map | 357 | referenced_symbols = inv_map |
| 348 | 358 | ||
| 349 | undefined = {} # {feature: [files]} | 359 | undefined = {} # {symbol: [files]} |
| 350 | for feature in sorted(referenced_features): | 360 | for symbol in sorted(referenced_symbols): |
| 351 | # filter some false positives | 361 | # filter some false positives |
| 352 | if feature == "FOO" or feature == "BAR" or \ | 362 | if symbol == "FOO" or symbol == "BAR" or \ |
| 353 | feature == "FOO_BAR" or feature == "XXX": | 363 | symbol == "FOO_BAR" or symbol == "XXX": |
| 354 | continue | 364 | continue |
| 355 | if feature not in defined_features: | 365 | if symbol not in defined_symbols: |
| 356 | if feature.endswith("_MODULE"): | 366 | if symbol.endswith("_MODULE"): |
| 357 | # avoid false positives for kernel modules | 367 | # avoid false positives for kernel modules |
| 358 | if feature[:-len("_MODULE")] in defined_features: | 368 | if symbol[:-len("_MODULE")] in defined_symbols: |
| 359 | continue | 369 | continue |
| 360 | undefined[feature] = referenced_features.get(feature) | 370 | undefined[symbol] = referenced_symbols.get(symbol) |
| 361 | return undefined, defined_features | 371 | return undefined, defined_symbols |
| 362 | 372 | ||
| 363 | 373 | ||
| 364 | def parse_source_files(source_files): | 374 | def parse_source_files(source_files): |
| 365 | """Parse each source file in @source_files and return dictionary with source | 375 | """Parse each source file in @source_files and return dictionary with source |
| 366 | files as keys and lists of references Kconfig symbols as values.""" | 376 | files as keys and lists of references Kconfig symbols as values.""" |
| 367 | referenced_features = dict() | 377 | referenced_symbols = dict() |
| 368 | for sfile in source_files: | 378 | for sfile in source_files: |
| 369 | referenced_features[sfile] = parse_source_file(sfile) | 379 | referenced_symbols[sfile] = parse_source_file(sfile) |
| 370 | return referenced_features | 380 | return referenced_symbols |
| 371 | 381 | ||
| 372 | 382 | ||
| 373 | def parse_source_file(sfile): | 383 | def parse_source_file(sfile): |
| 374 | """Parse @sfile and return a list of referenced Kconfig features.""" | 384 | """Parse @sfile and return a list of referenced Kconfig symbols.""" |
| 375 | lines = [] | 385 | lines = [] |
| 376 | references = [] | 386 | references = [] |
| 377 | 387 | ||
| 378 | if not os.path.exists(sfile): | 388 | if not os.path.exists(sfile): |
| 379 | return references | 389 | return references |
| 380 | 390 | ||
| 381 | with open(sfile, "r") as stream: | 391 | with open(sfile, "r", encoding='utf-8', errors='replace') as stream: |
| 382 | lines = stream.readlines() | 392 | lines = stream.readlines() |
| 383 | 393 | ||
| 384 | for line in lines: | 394 | for line in lines: |
| 385 | if not "CONFIG_" in line: | 395 | if "CONFIG_" not in line: |
| 386 | continue | 396 | continue |
| 387 | features = REGEX_SOURCE_FEATURE.findall(line) | 397 | symbols = REGEX_SOURCE_SYMBOL.findall(line) |
| 388 | for feature in features: | 398 | for symbol in symbols: |
| 389 | if not REGEX_FILTER_FEATURES.search(feature): | 399 | if not REGEX_FILTER_SYMBOLS.search(symbol): |
| 390 | continue | 400 | continue |
| 391 | references.append(feature) | 401 | references.append(symbol) |
| 392 | 402 | ||
| 393 | return references | 403 | return references |
| 394 | 404 | ||
| 395 | 405 | ||
| 396 | def get_features_in_line(line): | 406 | def get_symbols_in_line(line): |
| 397 | """Return mentioned Kconfig features in @line.""" | 407 | """Return mentioned Kconfig symbols in @line.""" |
| 398 | return REGEX_FEATURE.findall(line) | 408 | return REGEX_SYMBOL.findall(line) |
| 399 | 409 | ||
| 400 | 410 | ||
| 401 | def parse_kconfig_files(args): | 411 | def parse_kconfig_files(args): |
| @@ -404,21 +414,21 @@ def parse_kconfig_files(args): | |||
| 404 | pattern.""" | 414 | pattern.""" |
| 405 | kconfig_files = args[0] | 415 | kconfig_files = args[0] |
| 406 | ignore = args[1] | 416 | ignore = args[1] |
| 407 | defined_features = [] | 417 | defined_symbols = [] |
| 408 | referenced_features = dict() | 418 | referenced_symbols = dict() |
| 409 | 419 | ||
| 410 | for kfile in kconfig_files: | 420 | for kfile in kconfig_files: |
| 411 | defined, references = parse_kconfig_file(kfile) | 421 | defined, references = parse_kconfig_file(kfile) |
| 412 | defined_features.extend(defined) | 422 | defined_symbols.extend(defined) |
| 413 | if ignore and re.match(ignore, kfile): | 423 | if ignore and re.match(ignore, kfile): |
| 414 | # do not collect references for files that match the ignore pattern | 424 | # do not collect references for files that match the ignore pattern |
| 415 | continue | 425 | continue |
| 416 | referenced_features[kfile] = references | 426 | referenced_symbols[kfile] = references |
| 417 | return (defined_features, referenced_features) | 427 | return (defined_symbols, referenced_symbols) |
| 418 | 428 | ||
| 419 | 429 | ||
| 420 | def parse_kconfig_file(kfile): | 430 | def parse_kconfig_file(kfile): |
| 421 | """Parse @kfile and update feature definitions and references.""" | 431 | """Parse @kfile and update symbol definitions and references.""" |
| 422 | lines = [] | 432 | lines = [] |
| 423 | defined = [] | 433 | defined = [] |
| 424 | references = [] | 434 | references = [] |
| @@ -427,7 +437,7 @@ def parse_kconfig_file(kfile): | |||
| 427 | if not os.path.exists(kfile): | 437 | if not os.path.exists(kfile): |
| 428 | return defined, references | 438 | return defined, references |
| 429 | 439 | ||
| 430 | with open(kfile, "r") as stream: | 440 | with open(kfile, "r", encoding='utf-8', errors='replace') as stream: |
| 431 | lines = stream.readlines() | 441 | lines = stream.readlines() |
| 432 | 442 | ||
| 433 | for i in range(len(lines)): | 443 | for i in range(len(lines)): |
| @@ -436,8 +446,8 @@ def parse_kconfig_file(kfile): | |||
| 436 | line = line.split("#")[0] # ignore comments | 446 | line = line.split("#")[0] # ignore comments |
| 437 | 447 | ||
| 438 | if REGEX_KCONFIG_DEF.match(line): | 448 | if REGEX_KCONFIG_DEF.match(line): |
| 439 | feature_def = REGEX_KCONFIG_DEF.findall(line) | 449 | symbol_def = REGEX_KCONFIG_DEF.findall(line) |
| 440 | defined.append(feature_def[0]) | 450 | defined.append(symbol_def[0]) |
| 441 | skip = False | 451 | skip = False |
| 442 | elif REGEX_KCONFIG_HELP.match(line): | 452 | elif REGEX_KCONFIG_HELP.match(line): |
| 443 | skip = True | 453 | skip = True |
| @@ -446,18 +456,18 @@ def parse_kconfig_file(kfile): | |||
| 446 | pass | 456 | pass |
| 447 | elif REGEX_KCONFIG_STMT.match(line): | 457 | elif REGEX_KCONFIG_STMT.match(line): |
| 448 | line = REGEX_QUOTES.sub("", line) | 458 | line = REGEX_QUOTES.sub("", line) |
| 449 | features = get_features_in_line(line) | 459 | symbols = get_symbols_in_line(line) |
| 450 | # multi-line statements | 460 | # multi-line statements |
| 451 | while line.endswith("\\"): | 461 | while line.endswith("\\"): |
| 452 | i += 1 | 462 | i += 1 |
| 453 | line = lines[i] | 463 | line = lines[i] |
| 454 | line = line.strip('\n') | 464 | line = line.strip('\n') |
| 455 | features.extend(get_features_in_line(line)) | 465 | symbols.extend(get_symbols_in_line(line)) |
| 456 | for feature in set(features): | 466 | for symbol in set(symbols): |
| 457 | if REGEX_NUMERIC.match(feature): | 467 | if REGEX_NUMERIC.match(symbol): |
| 458 | # ignore numeric values | 468 | # ignore numeric values |
| 459 | continue | 469 | continue |
| 460 | references.append(feature) | 470 | references.append(symbol) |
| 461 | 471 | ||
| 462 | return defined, references | 472 | return defined, references |
| 463 | 473 | ||
diff --git a/scripts/ver_linux b/scripts/ver_linux index 0d8bd29b1bd6..430b201f3e25 100755 --- a/scripts/ver_linux +++ b/scripts/ver_linux | |||
| @@ -1,193 +1,89 @@ | |||
| 1 | #!/bin/sh | 1 | #!/bin/awk -f |
| 2 | # Before running this script please ensure that your PATH is | 2 | # Before running this script please ensure that your PATH is |
| 3 | # typical as you use for compilation/installation. I use | 3 | # typical as you use for compilation/installation. I use |
| 4 | # /bin /sbin /usr/bin /usr/sbin /usr/local/bin, but it may | 4 | # /bin /sbin /usr/bin /usr/sbin /usr/local/bin, but it may |
| 5 | # differ on your system. | 5 | # differ on your system. |
| 6 | # | ||
| 7 | echo 'If some fields are empty or look unusual you may have an old version.' | ||
| 8 | echo 'Compare to the current minimal requirements in Documentation/Changes.' | ||
| 9 | echo ' ' | ||
| 10 | 6 | ||
| 11 | uname -a | 7 | BEGIN { |
| 12 | echo ' ' | 8 | usage = "If some fields are empty or look unusual you may have an old version.\n" |
| 13 | 9 | usage = usage "Compare to the current minimal requirements in Documentation/Changes.\n" | |
| 14 | gcc -dumpversion 2>&1 | | 10 | print usage |
| 15 | awk '/[0-9]+([.]?[0-9]+)+/ && !/not found$/{ | 11 | |
| 16 | match($0, /[0-9]+([.]?[0-9]+)+/) | 12 | system("uname -a") |
| 17 | printf("GNU C\t\t\t%s\n", | 13 | printf("\n") |
| 18 | substr($0,RSTART,RLENGTH)) | 14 | |
| 19 | }' | 15 | printversion("GNU C", version("gcc -dumpversion 2>&1")) |
| 20 | 16 | printversion("GNU Make", version("make --version 2>&1")) | |
| 21 | make --version 2>&1 | | 17 | printversion("Binutils", version("ld -v 2>&1")) |
| 22 | awk '/GNU Make/{ | 18 | printversion("Util-linux", version("mount --version 2>&1")) |
| 23 | match($0, /[0-9]+([.]?[0-9]+)+/) | 19 | printversion("Mount", version("mount --version 2>&1")) |
| 24 | printf("GNU Make\t\t%s\n", | 20 | printversion("Module-init-tools", version("depmod -V 2>&1")) |
| 25 | substr($0,RSTART,RLENGTH)) | 21 | printversion("E2fsprogs", version("tune2fs 2>&1")) |
| 26 | }' | 22 | printversion("Jfsutils", version("fsck.jfs -V 2>&1")) |
| 27 | 23 | printversion("Reiserfsprogs", version("reiserfsck -V 2>&1")) | |
| 28 | ld -v 2>&1 | | 24 | printversion("Reiser4fsprogs", version("fsck.reiser4 -V 2>&1")) |
| 29 | awk '/[0-9]+([.]?[0-9]+)+/ && !/not found$/{ | 25 | printversion("Xfsprogs", version("xfs_db -V 2>&1")) |
| 30 | match($0, /[0-9]+([.]?[0-9]+)+/) | 26 | printversion("Pcmciautils", version("pccardctl -V 2>&1")) |
| 31 | printf("Binutils\t\t%s\n", | 27 | printversion("Pcmcia-cs", version("cardmgr -V 2>&1")) |
| 32 | substr($0,RSTART,RLENGTH)) | 28 | printversion("Quota-tools", version("quota -V 2>&1")) |
| 33 | }' | 29 | printversion("PPP", version("pppd --version 2>&1")) |
| 34 | 30 | printversion("Isdn4k-utils", version("isdnctrl 2>&1")) | |
| 35 | mount --version 2>&1 | | 31 | printversion("Nfs-utils", version("showmount --version 2>&1")) |
| 36 | awk '/[0-9]+([.]?[0-9]+)+/ && !/not found$/{ | 32 | |
| 37 | match($0, /[0-9]+([.]?[0-9]+)+/) | 33 | if (system("test -r /proc/self/maps") == 0) { |
| 38 | $0 = substr($0,RSTART,RLENGTH) | 34 | while (getline <"/proc/self/maps" > 0) { |
| 39 | printf("Util-linux\t\t%s\nMount\t\t\t%s\n",$0,$0) | 35 | n = split($0, procmaps, "/") |
| 40 | }' | 36 | if (/libc.*so$/ && match(procmaps[n], /[0-9]+([.]?[0-9]+)+/)) { |
| 41 | 37 | ver = substr(procmaps[n], RSTART, RLENGTH) | |
| 42 | depmod -V 2>&1 | | 38 | printversion("Linux C Library", ver) |
| 43 | awk '/[0-9]+([.]?[0-9]+)+/ && !/not found$/{ | 39 | break |
| 44 | match($0, /[0-9]+([.]?[0-9]+)+/) | 40 | } |
| 45 | printf("Module-init-tools\t%s\n", | 41 | } |
| 46 | substr($0,RSTART,RLENGTH)) | ||
| 47 | }' | ||
| 48 | |||
| 49 | tune2fs 2>&1 | | ||
| 50 | awk '/^tune2fs/{ | ||
| 51 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 52 | printf("E2fsprogs\t\t%s\n", | ||
| 53 | substr($0,RSTART,RLENGTH)) | ||
| 54 | }' | ||
| 55 | |||
| 56 | fsck.jfs -V 2>&1 | | ||
| 57 | awk '/version/{ | ||
| 58 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 59 | printf("Jfsutils\t\t%s\n", | ||
| 60 | substr($0,RSTART,RLENGTH)) | ||
| 61 | }' | ||
| 62 | |||
| 63 | reiserfsck -V 2>&1 | | ||
| 64 | awk '/^reiserfsck/{ | ||
| 65 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 66 | printf("Reiserfsprogs\t\t%s\n", | ||
| 67 | substr($0,RSTART,RLENGTH)) | ||
| 68 | }' | ||
| 69 | |||
| 70 | fsck.reiser4 -V 2>&1 | grep ^fsck.reiser4 | awk \ | ||
| 71 | 'NR==1{print "reiser4progs ", $2}' | ||
| 72 | |||
| 73 | xfs_db -V 2>&1 | | ||
| 74 | awk '/version/{ | ||
| 75 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 76 | printf("Xfsprogs\t\t%s\n", | ||
| 77 | substr($0,RSTART,RLENGTH)) | ||
| 78 | }' | ||
| 79 | |||
| 80 | pccardctl -V 2>&1 | | ||
| 81 | awk '/pcmciautils/{ | ||
| 82 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 83 | printf("Pcmciautils\t\t%s\n", | ||
| 84 | substr($0,RSTART,RLENGTH)) | ||
| 85 | }' | ||
| 86 | |||
| 87 | cardmgr -V 2>&1| grep version | awk \ | ||
| 88 | 'NR==1{print "pcmcia-cs ", $3}' | ||
| 89 | |||
| 90 | quota -V 2>&1 | | ||
| 91 | awk '/version/{ | ||
| 92 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 93 | printf("Quota-tools\t\t%s\n", | ||
| 94 | substr($0,RSTART,RLENGTH)) | ||
| 95 | }' | ||
| 96 | |||
| 97 | pppd --version 2>&1 | | ||
| 98 | awk '/version/{ | ||
| 99 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 100 | printf("PPP\t\t\t%s\n", | ||
| 101 | substr($0,RSTART,RLENGTH)) | ||
| 102 | }' | ||
| 103 | |||
| 104 | isdnctrl 2>&1 | grep version | awk \ | ||
| 105 | 'NR==1{print "isdn4k-utils ", $NF}' | ||
| 106 | |||
| 107 | showmount --version 2>&1 | grep nfs-utils | awk \ | ||
| 108 | 'NR==1{print "nfs-utils ", $NF}' | ||
| 109 | |||
| 110 | test -r /proc/self/maps && | ||
| 111 | sed ' | ||
| 112 | /.*libc-\(.*\)\.so$/!d | ||
| 113 | s//Linux C Library\t\t\1/ | ||
| 114 | q | ||
| 115 | ' /proc/self/maps | ||
| 116 | |||
| 117 | ldd --version 2>&1 | | ||
| 118 | awk '/^ldd/{ | ||
| 119 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 120 | printf("Dynamic linker (ldd)\t%s\n", | ||
| 121 | substr($0,RSTART,RLENGTH)) | ||
| 122 | }' | ||
| 123 | |||
| 124 | libcpp=`ldconfig -p 2>/dev/null | | ||
| 125 | awk '/(libg|stdc)[+]+\.so/ { | ||
| 126 | print $NF | ||
| 127 | exit | ||
| 128 | } | 42 | } |
| 129 | '` | ||
| 130 | test -r "$libcpp" && | ||
| 131 | ls -l $libcpp | | ||
| 132 | sed ' | ||
| 133 | s!.*so\.!! | ||
| 134 | s!^!Linux C++ Library\t! | ||
| 135 | ' | ||
| 136 | ps --version 2>&1 | | ||
| 137 | awk '/version/{ | ||
| 138 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 139 | printf("Procps\t\t\t%s\n", | ||
| 140 | substr($0,RSTART,RLENGTH)) | ||
| 141 | }' | ||
| 142 | |||
| 143 | ifconfig --version 2>&1 | | ||
| 144 | awk '/tools/{ | ||
| 145 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 146 | printf("Net-tools\t\t%s\n", | ||
| 147 | substr($0,RSTART,RLENGTH)) | ||
| 148 | }' | ||
| 149 | |||
| 150 | loadkeys -V 2>&1 | | ||
| 151 | awk '/[0-9]+([.]?[0-9]+)+/ && !/not found$/{ | ||
| 152 | match($0, /[0-9]+([.]?[0-9]+)+/) | ||
| 153 | $0 = substr($0,RSTART,RLENGTH) | ||
| 154 | printf("Kbd\t\t\t%s\nConsole-tools\t\t%s\n",$0,$0) | ||
| 155 | }' | ||
| 156 | 43 | ||
| 157 | oprofiled --version 2>&1 | awk \ | 44 | printversion("Dynamic linker (ldd)", version("ldd --version 2>&1")) |
| 158 | '(NR==1 && ($2 == "oprofile")) {print "oprofile ", $3}' | ||
| 159 | 45 | ||
| 160 | expr --v 2>&1 | | 46 | while ("ldconfig -p 2>/dev/null" | getline > 0) { |
| 161 | awk '/^expr/{ | 47 | if (/(libg|stdc)[+]+\.so/) { |
| 162 | match($0, /[0-9]+([.]?[0-9]+)+/) | 48 | libcpp = $NF |
| 163 | printf("Sh-utils\t\t%s\n", | 49 | break |
| 164 | substr($0,RSTART,RLENGTH)) | 50 | } |
| 165 | }' | 51 | } |
| 166 | 52 | if (system("test -r " libcpp) == 0) | |
| 167 | udevadm --version 2>&1 | | 53 | printversion("Linux C++ Library", version("readlink " libcpp)) |
| 168 | awk '/[0-9]+([.]?[0-9]+)+/ && !/not found$/{ | 54 | |
| 169 | match($0, /[0-9]+([.]?[0-9]+)+/) | 55 | printversion("Procps", version("ps --version 2>&1")) |
| 170 | printf("Udev\t\t\t%s\n", | 56 | printversion("Net-tools", version("ifconfig --version 2>&1")) |
| 171 | substr($0,RSTART,RLENGTH)) | 57 | printversion("Kbd", version("loadkeys -V 2>&1")) |
| 172 | }' | 58 | printversion("Console-tools", version("loadkeys -V 2>&1")) |
| 59 | printversion("Oprofile", version("oprofiled --version 2>&1")) | ||
| 60 | printversion("Sh-utils", version("expr --v 2>&1")) | ||
| 61 | printversion("Udev", version("udevadm --version 2>&1")) | ||
| 62 | printversion("Wireless-tools", version("iwconfig --version 2>&1")) | ||
| 63 | |||
| 64 | if (system("test -r /proc/modules") == 0) { | ||
| 65 | while ("sort /proc/modules" | getline > 0) { | ||
| 66 | mods = mods sep $1 | ||
| 67 | sep = " " | ||
| 68 | } | ||
| 69 | printversion("Modules Loaded", mods) | ||
| 70 | } | ||
| 71 | } | ||
| 173 | 72 | ||
| 174 | iwconfig --version 2>&1 | | 73 | function version(cmd, ver) { |
| 175 | awk '/version/{ | 74 | while (cmd | getline > 0) { |
| 176 | match($0, /[0-9]+([.]?[0-9]+)+/) | 75 | if (!/ver_linux/ && match($0, /[0-9]+([.]?[0-9]+)+/)) { |
| 177 | printf("Wireless-tools\t\t%s\n", | 76 | ver = substr($0, RSTART, RLENGTH) |
| 178 | substr($0,RSTART,RLENGTH)) | 77 | break |
| 179 | }' | 78 | } |
| 79 | } | ||
| 80 | close(cmd) | ||
| 81 | return ver | ||
| 82 | } | ||
| 180 | 83 | ||
| 181 | test -e /proc/modules && | 84 | function printversion(name, value, ofmt) { |
| 182 | sort /proc/modules | | 85 | if (value != "") { |
| 183 | sed ' | 86 | ofmt = "%-20s\t%s\n" |
| 184 | s/ .*// | 87 | printf(ofmt, name, value) |
| 185 | H | 88 | } |
| 186 | ${ | ||
| 187 | g | ||
| 188 | s/^\n/Modules Loaded\t\t/ | ||
| 189 | y/\n/ / | ||
| 190 | q | ||
| 191 | } | 89 | } |
| 192 | d | ||
| 193 | ' | ||
