xref: /llvm-project/llvm/utils/lint/common_lint.py (revision 900be9013fdc3bab9fce906f8a71e59ecd8873b4)
1#!/usr/bin/env python
2#
3# Common lint functions applicable to multiple types of files.
4
5from __future__ import print_function
6import re
7
8
9def VerifyLineLength(filename, lines, max_length):
10    """Checks to make sure the file has no lines with lines exceeding the length
11    limit.
12
13    Args:
14      filename: the file under consideration as string
15      lines: contents of the file as string array
16      max_length: maximum acceptable line length as number
17
18    Returns:
19      A list of tuples with format [(filename, line number, msg), ...] with any
20      violations found.
21    """
22    lint = []
23    line_num = 1
24    for line in lines:
25        length = len(line.rstrip("\n"))
26        if length > max_length:
27            lint.append(
28                (
29                    filename,
30                    line_num,
31                    "Line exceeds %d chars (%d)" % (max_length, length),
32                )
33            )
34        line_num += 1
35    return lint
36
37
38def VerifyTabs(filename, lines):
39    """Checks to make sure the file has no tab characters.
40
41    Args:
42      filename: the file under consideration as string
43      lines: contents of the file as string array
44
45    Returns:
46      A list of tuples with format [(line_number, msg), ...] with any violations
47      found.
48    """
49    lint = []
50    tab_re = re.compile(r"\t")
51    line_num = 1
52    for line in lines:
53        if tab_re.match(line.rstrip("\n")):
54            lint.append((filename, line_num, "Tab found instead of whitespace"))
55        line_num += 1
56    return lint
57
58
59def VerifyTrailingWhitespace(filename, lines):
60    """Checks to make sure the file has no lines with trailing whitespace.
61
62    Args:
63      filename: the file under consideration as string
64      lines: contents of the file as string array
65
66    Returns:
67      A list of tuples with format [(filename, line number, msg), ...] with any
68      violations found.
69    """
70    lint = []
71    trailing_whitespace_re = re.compile(r"\s+$")
72    line_num = 1
73    for line in lines:
74        if trailing_whitespace_re.match(line.rstrip("\n")):
75            lint.append((filename, line_num, "Trailing whitespace"))
76        line_num += 1
77    return lint
78
79
80class BaseLint:
81    def RunOnFile(filename, lines):
82        raise Exception("RunOnFile() unimplemented")
83
84
85def RunLintOverAllFiles(linter, filenames):
86    """Runs linter over the contents of all files.
87
88    Args:
89      lint: subclass of BaseLint, implementing RunOnFile()
90      filenames: list of all files whose contents will be linted
91
92    Returns:
93      A list of tuples with format [(filename, line number, msg), ...] with any
94      violations found.
95    """
96    lint = []
97    for filename in filenames:
98        file = open(filename, "r")
99        if not file:
100            print("Could not open %s" % filename)
101            continue
102        lines = file.readlines()
103        lint.extend(linter.RunOnFile(filename, lines))
104
105    return lint
106