3
# cpplint.py is Copyright (C) 2009 Google Inc.
5
# It is free software; you can redistribute it and/or modify it under the
8
# a) the GNU General Public License as published by the Free Software
10
# This program is free software; you can redistribute it and/or modify
11
# it under the terms of the GNU General Public License as published by
12
# the Free Software Foundation; version 2 of the License.
16
# b) the "Artistic License".
18
# Modified for Drizzle by Monty Taylor & Robert Collins
20
# Here are some issues that I've had people identify in my code during reviews,
21
# that I think are possible to flag automatically in a lint tool. If these were
22
# caught by lint, it would save time both for myself and that of my reviewers.
23
# Most likely, some of these are beyond the scope of the current lint framework,
24
# but I think it is valuable to retain these wish-list items even if they cannot
25
# be immediately implemented.
29
# - Check for no 'explicit' for multi-arg ctor
30
# - Check for boolean assign RHS in parens
31
# - Check for ctor initializer-list colon position and spacing
32
# - Check that if there's a ctor, there should be a dtor
33
# - Check accessors that return non-pointer member variables are
35
# - Check accessors that return non-const pointer member vars are
36
# *not* declared const
37
# - Check for using public includes for testing
38
# - Check for spaces between brackets in one-line inline method
39
# - Check for no assert()
40
# - Check for spaces surrounding operators
41
# - Check for 0 in pointer context (should be NULL)
42
# - Check for 0 in char context (should be '\0')
43
# - Check for camel-case method name conventions for methods
44
# that are not simple inline getters and setters
45
# - Check that base classes have virtual destructors
46
# put " // namespace" after } that closes a namespace, with
47
# namespace's name after 'namespace' if it is named.
48
# - Do not indent namespace contents
49
# - Avoid inlining non-trivial constructors in header files
50
# include base/basictypes.h if DISALLOW_EVIL_CONSTRUCTORS is used
51
# - Check for old-school (void) cast for call-sites of functions
52
# ignored return value
53
# - Check gUnit usage of anonymous namespace
54
# - Check for class declaration order (typedefs, consts, enums,
55
# ctor(s?), dtor, friend declarations, methods, member vars)
58
"""Does google-lint on c++ files.
60
The goal of this script is to identify places in the code that *may*
61
be in non-compliance with google style. It does not attempt to fix
62
up these problems -- the point is to educate. It does also not
63
attempt to find all problems, or to ensure that everything it does
64
find is legitimately a problem.
66
In particular, we can get very confused by /* and // inside strings!
67
We do a small hack, which is to ignore //'s with "'s after them on the
68
same line, but it is far from perfect (in either direction).
83
Syntax: cpplint.py [--verbose=#] [--output=vs7] [--deps=path] [--filter=-x,+y,...]
86
The style guidelines this tries to follow are those in
87
http://google-styleguide.googlecode.com/svn/trunk/cppguide.xml
89
Every problem is given a confidence score from 1-5, with 5 meaning we are
90
certain of the problem, and 1 meaning it could be a legitimate construct.
91
This will miss some errors, and is not a substitute for a code review.
93
To prevent specific lines from being linted, add a '// NOLINT' comment to the
96
The files passed in will be linted; at least one file must be provided.
97
Linted extensions are .cc, .cpp, and .h. Other file types will be ignored.
102
By default, the output is formatted to ease emacs parsing. Visual Studio
103
compatible output (vs7) may also be used. Other formats are unsupported.
106
Specify a number 0-5 to restrict errors to certain verbosity levels.
109
write out a Makefile that can be included listing the files included
110
during the lint process as make style dependencies with null-build rules
111
(so that deleted headers will not cause failures). This can be useful to
112
perform on-demand linting. The top level target will be the name of the
116
Specify a comma-separated list of category-filters to apply: only
117
error messages whose category names pass the filters will be printed.
118
(Category names are printed with the message and look like
119
"[whitespace/indent]".) Filters are evaluated left to right.
120
"-FOO" and "FOO" means "do not print categories that start with FOO".
121
"+FOO" means "do print categories that start with FOO".
123
Examples: --filter=-whitespace,+whitespace/braces
124
--filter=whitespace,runtime/printf,+runtime/printf_format
125
--filter=-,+build/include_what_you_use
127
To see a list of all the categories used in cpplint, pass no arg:
131
# We categorize each error message we print. Here are the categories.
132
# We want an explicit list so we can list them all in cpplint --filter=.
133
# If you add a new error message with a new category, add it to the list
134
# here! cpplint_unittest.py should tell you if you forget to do this.
135
# \ used for clearer layout -- pylint: disable-msg=C6013
136
_ERROR_CATEGORIES = '''\
145
build/include_what_you_use
153
readability/constructors
156
readability/multiline_comment
157
readability/multiline_string
166
runtime/invalid_increment
169
runtime/printf_format
174
runtime/threadsafe_fn
176
whitespace/blank_line
180
whitespace/end_of_line
181
whitespace/ending_newline
184
whitespace/line_length
193
# The default state of the category filter. This is overrided by the --filter=
194
# flag. By default all errors are on, so only add here categories that should be
195
# off by default (i.e., categories that must be enabled by the --filter= flags).
196
# All entries here should start with a '-' or '+', as in the --filter= flag.
197
_DEFAULT_FILTERS = []
199
# We used to check for high-bit characters, but after much discussion we
200
# decided those were OK, as long as they were in UTF-8 and didn't represent
201
# hard-coded international strings, which belong in a seperate i18n file.
203
# Headers that we consider STL headers.
204
_STL_HEADERS = frozenset([
205
'algobase.h', 'algorithm', 'alloc.h', 'bitset', 'deque', 'exception',
206
'function.h', 'functional', 'hash_map', 'hash_map.h', 'hash_set',
207
'hash_set.h', 'iterator', 'list', 'list.h', 'map', 'memory', 'pair.h',
208
'pthread_alloc', 'queue', 'set', 'set.h', 'sstream', 'stack',
209
'stl_alloc.h', 'stl_relops.h', 'type_traits.h',
210
'utility', 'vector', 'vector.h',
214
# Non-STL C++ system headers.
215
_CPP_HEADERS = frozenset([
216
'algo.h', 'builtinbuf.h', 'bvector.h', 'cassert', 'cctype',
217
'cerrno', 'cfloat', 'ciso646', 'climits', 'clocale', 'cmath',
218
'complex', 'complex.h', 'csetjmp', 'csignal', 'cstdarg', 'cstddef',
219
'cstdio', 'cstdlib', 'cstring', 'ctime', 'cwchar', 'cwctype',
220
'defalloc.h', 'deque.h', 'editbuf.h', 'exception', 'fstream',
221
'fstream.h', 'hashtable.h', 'heap.h', 'indstream.h', 'iomanip',
222
'iomanip.h', 'ios', 'iosfwd', 'iostream', 'iostream.h', 'istream.h',
223
'iterator.h', 'limits', 'map.h', 'multimap.h', 'multiset.h',
224
'numeric', 'ostream.h', 'parsestream.h', 'pfstream.h', 'PlotFile.h',
225
'procbuf.h', 'pthread_alloc.h', 'rope', 'rope.h', 'ropeimpl.h',
226
'SFile.h', 'slist', 'slist.h', 'stack.h', 'stdexcept',
227
'stdiostream.h', 'streambuf.h', 'stream.h', 'strfile.h', 'string',
228
'strstream', 'strstream.h', 'tempbuf.h', 'tree.h', 'typeinfo', 'valarray',
232
# Assertion macros. These are defined in base/logging.h and
233
# testing/base/gunit.h. Note that the _M versions need to come first
234
# for substring matching to work.
237
'EXPECT_TRUE_M', 'EXPECT_TRUE',
238
'ASSERT_TRUE_M', 'ASSERT_TRUE',
239
'EXPECT_FALSE_M', 'EXPECT_FALSE',
240
'ASSERT_FALSE_M', 'ASSERT_FALSE',
243
# Replacement macros for CHECK/DCHECK/EXPECT_TRUE/EXPECT_FALSE
244
_CHECK_REPLACEMENT = dict([(m, {}) for m in _CHECK_MACROS])
246
for op, replacement in [('==', 'EQ'), ('!=', 'NE'),
247
('>=', 'GE'), ('>', 'GT'),
248
('<=', 'LE'), ('<', 'LT')]:
249
_CHECK_REPLACEMENT['DCHECK'][op] = 'DCHECK_%s' % replacement
250
_CHECK_REPLACEMENT['CHECK'][op] = 'CHECK_%s' % replacement
251
_CHECK_REPLACEMENT['EXPECT_TRUE'][op] = 'EXPECT_%s' % replacement
252
_CHECK_REPLACEMENT['ASSERT_TRUE'][op] = 'ASSERT_%s' % replacement
253
_CHECK_REPLACEMENT['EXPECT_TRUE_M'][op] = 'EXPECT_%s_M' % replacement
254
_CHECK_REPLACEMENT['ASSERT_TRUE_M'][op] = 'ASSERT_%s_M' % replacement
256
for op, inv_replacement in [('==', 'NE'), ('!=', 'EQ'),
257
('>=', 'LT'), ('>', 'LE'),
258
('<=', 'GT'), ('<', 'GE')]:
259
_CHECK_REPLACEMENT['EXPECT_FALSE'][op] = 'EXPECT_%s' % inv_replacement
260
_CHECK_REPLACEMENT['ASSERT_FALSE'][op] = 'ASSERT_%s' % inv_replacement
261
_CHECK_REPLACEMENT['EXPECT_FALSE_M'][op] = 'EXPECT_%s_M' % inv_replacement
262
_CHECK_REPLACEMENT['ASSERT_FALSE_M'][op] = 'ASSERT_%s_M' % inv_replacement
265
# These constants define types of headers for use with
266
# _IncludeState.CheckNextIncludeOrder().
269
_LIKELY_MY_HEADER = 3
270
_POSSIBLE_MY_HEADER = 4
274
_regexp_compile_cache = {}
277
def Match(pattern, s):
278
"""Matches the string with the pattern, caching the compiled regexp."""
279
# The regexp compilation caching is inlined in both Match and Search for
280
# performance reasons; factoring it out into a separate function turns out
281
# to be noticeably expensive.
282
if not pattern in _regexp_compile_cache:
283
_regexp_compile_cache[pattern] = sre_compile.compile(pattern)
284
return _regexp_compile_cache[pattern].match(s)
287
def Search(pattern, s):
288
"""Searches the string for the pattern, caching the compiled regexp."""
289
if not pattern in _regexp_compile_cache:
290
_regexp_compile_cache[pattern] = sre_compile.compile(pattern)
291
return _regexp_compile_cache[pattern].search(s)
294
class _IncludeState(dict):
295
"""Tracks line numbers for includes, and the order in which includes appear.
297
As a dict, an _IncludeState object serves as a mapping between include
298
filename and line number on which that file was included.
300
Call CheckNextIncludeOrder() once for each header in the file, passing
301
in the type constants defined above. Calls in an illegal order will
302
raise an _IncludeError with an appropriate error message.
305
# self._section will move monotonically through this set. If it ever
306
# needs to move backwards, CheckNextIncludeOrder will raise an error.
314
_C_SYS_HEADER: 'C system header',
315
_CPP_SYS_HEADER: 'C++ system header',
316
_LIKELY_MY_HEADER: 'header this file implements',
317
_POSSIBLE_MY_HEADER: 'header this file may implement',
318
_OTHER_HEADER: 'other header',
321
_INITIAL_SECTION: "... nothing. (This can't be an error.)",
322
_MY_H_SECTION: 'a header this file implements',
323
_C_SECTION: 'C system header',
324
_CPP_SECTION: 'C++ system header',
325
_OTHER_H_SECTION: 'other header',
330
self._section = self._INITIAL_SECTION
332
def CheckNextIncludeOrder(self, header_type):
333
"""Returns a non-empty error message if the next header is out of order.
335
This function also updates the internal state to be ready to check
339
header_type: One of the _XXX_HEADER constants defined above.
342
The empty string if the header is in the right order, or an
343
error message describing what's wrong.
346
error_message = ('Found %s after %s' %
347
(self._TYPE_NAMES[header_type],
348
self._SECTION_NAMES[self._section]))
350
if header_type == _C_SYS_HEADER:
351
if self._section <= self._C_SECTION:
352
self._section = self._C_SECTION
355
elif header_type == _CPP_SYS_HEADER:
356
if self._section <= self._CPP_SECTION:
357
self._section = self._CPP_SECTION
360
elif header_type == _LIKELY_MY_HEADER:
361
if self._section <= self._MY_H_SECTION:
362
self._section = self._MY_H_SECTION
364
self._section = self._OTHER_H_SECTION
365
elif header_type == _POSSIBLE_MY_HEADER:
366
if self._section <= self._MY_H_SECTION:
367
self._section = self._MY_H_SECTION
369
# This will always be the fallback because we're not sure
370
# enough that the header is associated with this file.
371
self._section = self._OTHER_H_SECTION
373
assert header_type == _OTHER_HEADER
374
self._section = self._OTHER_H_SECTION
379
class _CppLintState(object):
380
"""Maintains module-wide state.."""
383
self.verbose_level = 1 # global setting.
384
self.error_count = 0 # global count of reported errors
385
# filters to apply when emitting error messages
386
self.filters = _DEFAULT_FILTERS[:]
389
# "emacs" - format that emacs can parse (default)
390
# "vs7" - format that Microsoft Visual Studio 7 can parse
391
self.output_format = 'emacs'
394
self.depfilename = None
395
self.seen_fnames = set()
398
"""Complete things that wait for the end of the lint operation."""
399
if self.depfilename is not None:
401
# Don't alter dependency data
403
depfile = file(self.depfilename, 'w+')
404
# depend on what we read
405
depfile.write("%s: " % self.depfilename)
406
names = sorted(self.seen_fnames)
407
depfile.write(' '.join(names))
409
# anything we read shouldn't cause an error if its missing - so claim
412
depfile.write('%s:\n' % name)
415
def seen_file(self, fname):
416
self.seen_fnames.add(fname)
418
def SetOutputFormat(self, output_format):
419
"""Sets the output format for errors."""
420
self.output_format = output_format
422
def SetVerboseLevel(self, level):
423
"""Sets the module's verbosity, and returns the previous setting."""
424
last_verbose_level = self.verbose_level
425
self.verbose_level = level
426
return last_verbose_level
428
def SetFilters(self, filters):
429
"""Sets the error-message filters.
431
These filters are applied when deciding whether to emit a given
435
filters: A string of comma-separated filters (eg "+whitespace/indent").
436
Each filter should start with + or -; else we die.
439
ValueError: The comma-separated filters did not all start with '+' or '-'.
440
E.g. "-,+whitespace,-whitespace/indent,whitespace/badfilter"
442
# Default filters always have less priority than the flag ones.
443
self.filters = _DEFAULT_FILTERS[:]
444
for filt in filters.split(','):
445
clean_filt = filt.strip()
447
self.filters.append(clean_filt)
448
for filt in self.filters:
449
if not (filt.startswith('+') or filt.startswith('-')):
450
raise ValueError('Every filter in --filters must start with + or -'
451
' (%s does not)' % filt)
453
def ResetErrorCount(self):
454
"""Sets the module's error statistic back to zero."""
457
def IncrementErrorCount(self):
458
"""Bumps the module's error statistic."""
459
self.error_count += 1
462
_cpplint_state = _CppLintState()
466
"""Gets the module's output format."""
467
return _cpplint_state.output_format
470
def _SetOutputFormat(output_format):
471
"""Sets the module's output format."""
472
_cpplint_state.SetOutputFormat(output_format)
476
"""Returns the module's verbosity setting."""
477
return _cpplint_state.verbose_level
480
def _SetVerboseLevel(level):
481
"""Sets the module's verbosity, and returns the previous setting."""
482
return _cpplint_state.SetVerboseLevel(level)
486
"""Returns the module's list of output filters, as a list."""
487
return _cpplint_state.filters
490
def _SetFilters(filters):
491
"""Sets the module's error-message filters.
493
These filters are applied when deciding whether to emit a given
497
filters: A string of comma-separated filters (eg "whitespace/indent").
498
Each filter should start with + or -; else we die.
500
_cpplint_state.SetFilters(filters)
503
class _FunctionState(object):
504
"""Tracks current function name and the number of lines in its body."""
506
_NORMAL_TRIGGER = 250 # for --v=0, 500 for --v=1, etc.
507
_TEST_TRIGGER = 400 # about 50% more than _NORMAL_TRIGGER.
510
self.in_a_function = False
511
self.lines_in_function = 0
512
self.current_function = ''
514
def Begin(self, function_name):
515
"""Start analyzing function body.
518
function_name: The name of the function being tracked.
520
self.in_a_function = True
521
self.lines_in_function = 0
522
self.current_function = function_name
525
"""Count line in current function body."""
526
if self.in_a_function:
527
self.lines_in_function += 1
529
def Check(self, error, filename, linenum):
530
"""Report if too many lines in function body.
533
error: The function to call with any errors found.
534
filename: The name of the current file.
535
linenum: The number of the line to check.
537
if Match(r'T(EST|est)', self.current_function):
538
base_trigger = self._TEST_TRIGGER
540
base_trigger = self._NORMAL_TRIGGER
541
trigger = base_trigger * 2**_VerboseLevel()
543
if self.lines_in_function > trigger:
544
error_level = int(math.log(self.lines_in_function / base_trigger, 2))
545
# 50 => 0, 100 => 1, 200 => 2, 400 => 3, 800 => 4, 1600 => 5, ...
548
error(filename, linenum, 'readability/fn_size', error_level,
549
'Small and focused functions are preferred:'
550
' %s has %d non-comment lines'
551
' (error triggered by exceeding %d lines).' % (
552
self.current_function, self.lines_in_function, trigger))
555
"""Stop analizing function body."""
556
self.in_a_function = False
559
class _IncludeError(Exception):
560
"""Indicates a problem with the include order in a file."""
565
"""Provides utility functions for filenames.
567
FileInfo provides easy access to the components of a file's path
568
relative to the project root.
571
def __init__(self, filename):
572
self._filename = filename
575
"""Make Windows paths like Unix."""
576
return os.path.abspath(self._filename).replace('\\', '/')
578
def RepositoryName(self):
579
"""FullName after removing the local path to the repository.
581
If we have a real absolute path name here we can try to do something smart:
582
detecting the root of the checkout and truncating /path/to/checkout from
583
the name so that we get header guards that don't include things like
584
"C:\Documents and Settings\..." or "/home/username/..." in them and thus
585
people on different computers who have checked the source out to different
586
locations won't see bogus errors.
588
fullname = self.FullName()
590
if os.path.exists(fullname):
591
project_dir = os.path.dirname(fullname)
593
root_dir = os.path.dirname(fullname)
594
while (root_dir != os.path.dirname(root_dir) and
595
not (os.path.exists(os.path.join(root_dir, ".bzr"))
597
os.path.exists(os.path.join(root_dir, "_build")))):
598
root_dir = os.path.dirname(root_dir)
599
if (os.path.exists(os.path.join(root_dir, ".bzr")) or
600
os.path.exists(os.path.join(root_dir, "_build"))):
601
prefix = os.path.commonprefix([root_dir, project_dir])
602
return fullname[len(prefix) + 1:]
604
# Don't know what to do; header guard warnings may be wrong...
608
"""Splits the file into the directory, basename, and extension.
610
For 'chrome/browser/browser.cc', Split() would
611
return ('chrome/browser', 'browser', '.cc')
614
A tuple of (directory, basename, extension).
617
googlename = self.RepositoryName()
618
project, rest = os.path.split(googlename)
619
return (project,) + os.path.splitext(rest)
622
"""File base name - text after the final slash, before the final period."""
623
return self.Split()[1]
626
"""File extension - text following the final period."""
627
return self.Split()[2]
629
def NoExtension(self):
630
"""File has no source file extension."""
631
return '/'.join(self.Split()[0:2])
634
"""File has a source file extension."""
635
return self.Extension()[1:] in ('c', 'cc', 'cpp', 'cxx')
638
def _ShouldPrintError(category, confidence):
639
"""Returns true iff confidence >= verbose, and category passes filter."""
640
# There are two ways we might decide not to print an error message:
641
# the verbosity level isn't high enough, or the filters filter it out.
642
if confidence < _cpplint_state.verbose_level:
646
for one_filter in _Filters():
647
if one_filter.startswith('-'):
648
if category.startswith(one_filter[1:]):
650
elif one_filter.startswith('+'):
651
if category.startswith(one_filter[1:]):
654
assert False # should have been checked for in SetFilter.
661
def Error(filename, linenum, category, confidence, message):
662
"""Logs the fact we've found a lint error.
664
We log where the error was found, and also our confidence in the error,
665
that is, how certain we are this is a legitimate style regression, and
666
not a misidentification or a use that's sometimes justified.
669
filename: The name of the file containing the error.
670
linenum: The number of the line containing the error.
671
category: A string used to describe the "category" this bug
672
falls under: "whitespace", say, or "runtime". Categories
673
may have a hierarchy separated by slashes: "whitespace/indent".
674
confidence: A number from 1-5 representing a confidence score for
675
the error, with 5 meaning that we are certain of the problem,
676
and 1 meaning that it could be a legitimate construct.
677
message: The error message.
679
# There are two ways we might decide not to print an error message:
680
# the verbosity level isn't high enough, or the filters filter it out.
681
if _ShouldPrintError(category, confidence):
682
_cpplint_state.IncrementErrorCount()
683
if _cpplint_state.output_format == 'vs7':
684
sys.stderr.write('%s(%s): %s [%s] [%d]\n' % (
685
filename, linenum, message, category, confidence))
687
sys.stderr.write('%s:%s: %s [%s] [%d]\n' % (
688
filename, linenum, message, category, confidence))
691
# Matches standard C++ escape esequences per 2.13.2.3 of the C++ standard.
692
_RE_PATTERN_CLEANSE_LINE_ESCAPES = re.compile(
693
r'\\([abfnrtv?"\\\']|\d+|x[0-9a-fA-F]+)')
694
# Matches strings. Escape codes should already be removed by ESCAPES.
695
_RE_PATTERN_CLEANSE_LINE_DOUBLE_QUOTES = re.compile(r'"[^"]*"')
696
# Matches characters. Escape codes should already be removed by ESCAPES.
697
_RE_PATTERN_CLEANSE_LINE_SINGLE_QUOTES = re.compile(r"'.'")
698
# Matches multi-line C++ comments.
699
# This RE is a little bit more complicated than one might expect, because we
700
# have to take care of space removals tools so we can handle comments inside
702
# The current rule is: We only clear spaces from both sides when we're at the
703
# end of the line. Otherwise, we try to remove spaces from the right side,
704
# if this doesn't work we try on left side but only if there's a non-character
706
_RE_PATTERN_CLEANSE_LINE_C_COMMENTS = re.compile(
707
r"""(\s*/\*.*\*/\s*$|
710
/\*.*\*/)""", re.VERBOSE)
713
def IsCppString(line):
714
"""Does line terminate so, that the next symbol is in string constant.
716
This function does not consider single-line nor multi-line comments.
719
line: is a partial line of code starting from the 0..n.
722
True, if next character appended to 'line' is inside a
726
line = line.replace(r'\\', 'XX') # after this, \\" does not match to \"
727
return ((line.count('"') - line.count(r'\"') - line.count("'\"'")) & 1) == 1
730
def FindNextMultiLineCommentStart(lines, lineix):
731
"""Find the beginning marker for a multiline comment."""
732
while lineix < len(lines):
733
if lines[lineix].strip().startswith('/*'):
734
# Only return this marker if the comment goes beyond this line
735
if lines[lineix].strip().find('*/', 2) < 0:
741
def FindNextMultiLineCommentEnd(lines, lineix):
742
"""We are inside a comment, find the end marker."""
743
while lineix < len(lines):
744
if lines[lineix].strip().endswith('*/'):
750
def RemoveMultiLineCommentsFromRange(lines, begin, end):
751
"""Clears a range of lines for multi-line comments."""
752
# Having // dummy comments makes the lines non-empty, so we will not get
753
# unnecessary blank line warnings later in the code.
754
for i in range(begin, end):
755
lines[i] = '// dummy'
758
def RemoveMultiLineComments(filename, lines, error):
759
"""Removes multiline (c-style) comments from lines."""
761
while lineix < len(lines):
762
lineix_begin = FindNextMultiLineCommentStart(lines, lineix)
763
if lineix_begin >= len(lines):
765
lineix_end = FindNextMultiLineCommentEnd(lines, lineix_begin)
766
if lineix_end >= len(lines):
767
error(filename, lineix_begin + 1, 'readability/multiline_comment', 5,
768
'Could not find end of multi-line comment')
770
RemoveMultiLineCommentsFromRange(lines, lineix_begin, lineix_end + 1)
771
lineix = lineix_end + 1
774
def CleanseComments(line):
775
"""Removes //-comments and single-line C-style /* */ comments.
778
line: A line of C++ source.
781
The line with single-line comments removed.
783
commentpos = line.find('//')
784
if commentpos != -1 and not IsCppString(line[:commentpos]):
785
line = line[:commentpos]
786
# get rid of /* ... */
787
return _RE_PATTERN_CLEANSE_LINE_C_COMMENTS.sub('', line)
790
class CleansedLines(object):
791
"""Holds 3 copies of all lines with different preprocessing applied to them.
793
1) elided member contains lines without strings and comments,
794
2) lines member contains lines without comments, and
795
3) raw member contains all the lines without processing.
796
All these three members are of <type 'list'>, and of the same length.
799
def __init__(self, lines):
802
self.raw_lines = lines
803
self.num_lines = len(lines)
804
for linenum in range(len(lines)):
805
self.lines.append(CleanseComments(lines[linenum]))
806
elided = self._CollapseStrings(lines[linenum])
807
self.elided.append(CleanseComments(elided))
810
"""Returns the number of lines represented."""
811
return self.num_lines
814
def _CollapseStrings(elided):
815
"""Collapses strings and chars on a line to simple "" or '' blocks.
817
We nix strings first so we're not fooled by text like '"http://"'
820
elided: The line being processed.
823
The line with collapsed strings.
825
if not _RE_PATTERN_INCLUDE.match(elided):
826
# Remove escaped characters first to make quote/single quote collapsing
827
# basic. Things that look like escaped characters shouldn't occur
828
# outside of strings and chars.
829
elided = _RE_PATTERN_CLEANSE_LINE_ESCAPES.sub('', elided)
830
elided = _RE_PATTERN_CLEANSE_LINE_SINGLE_QUOTES.sub("''", elided)
831
elided = _RE_PATTERN_CLEANSE_LINE_DOUBLE_QUOTES.sub('""', elided)
835
def CloseExpression(clean_lines, linenum, pos):
836
"""If input points to ( or { or [, finds the position that closes it.
838
If lines[linenum][pos] points to a '(' or '{' or '[', finds the the
839
linenum/pos that correspond to the closing of the expression.
842
clean_lines: A CleansedLines instance containing the file.
843
linenum: The number of the line to check.
844
pos: A position on the line.
847
A tuple (line, linenum, pos) pointer *past* the closing brace, or
848
(line, len(lines), -1) if we never find a close. Note we ignore
849
strings and comments when matching; and the line we return is the
850
'cleansed' line at linenum.
853
line = clean_lines.elided[linenum]
854
startchar = line[pos]
855
if startchar not in '({[':
856
return (line, clean_lines.NumLines(), -1)
857
if startchar == '(': endchar = ')'
858
if startchar == '[': endchar = ']'
859
if startchar == '{': endchar = '}'
861
num_open = line.count(startchar) - line.count(endchar)
862
while linenum < clean_lines.NumLines() and num_open > 0:
864
line = clean_lines.elided[linenum]
865
num_open += line.count(startchar) - line.count(endchar)
866
# OK, now find the endchar that actually got us back to even
869
endpos = line.rfind(')', 0, endpos)
870
num_open -= 1 # chopped off another )
871
return (line, linenum, endpos + 1)
874
def CheckForCopyright(filename, lines, error):
875
"""Logs an error if no Copyright message appears at the top of the file."""
877
# We'll say it should occur by line 10. Don't forget there's a
878
# dummy line at the front.
879
for line in xrange(1, min(len(lines), 11)):
880
if re.search(r'Copyright', lines[line], re.I): break
881
else: # means no copyright line was found
882
error(filename, 0, 'legal/copyright', 5,
883
'No copyright message found. '
884
'You should have a line: "Copyright [year] <Copyright Owner>"')
887
def GetHeaderGuardCPPVariable(filename):
888
"""Returns the CPP variable that should be used as a header guard.
891
filename: The name of a C++ header file.
894
The CPP variable that should be used as a header guard in the
899
fileinfo = FileInfo(filename)
900
return re.sub(r'[-./\s]', '_', fileinfo.RepositoryName()).upper()
903
def CheckForHeaderGuard(filename, lines, error):
904
"""Checks that the file contains a header guard.
906
Logs an error if no #ifndef header guard is present. For other
907
headers, checks that the full pathname is used.
910
filename: The name of the C++ header file.
911
lines: An array of strings, each representing a line of the file.
912
error: The function to call with any errors found.
915
cppvar = GetHeaderGuardCPPVariable(filename)
922
for linenum, line in enumerate(lines):
923
linesplit = line.split()
924
if len(linesplit) >= 2:
925
# find the first occurrence of #ifndef and #define, save arg
926
if not ifndef and linesplit[0] == '#ifndef':
927
# set ifndef to the header guard presented on the #ifndef line.
928
ifndef = linesplit[1]
929
ifndef_linenum = linenum
930
if not define and linesplit[0] == '#define':
931
define = linesplit[1]
932
# find the last occurrence of #endif, save entire line
933
if line.startswith('#endif'):
935
endif_linenum = linenum
937
if not ifndef or not define or ifndef != define:
938
error(filename, 0, 'build/header_guard', 5,
939
'No #ifndef header guard found, suggested CPP variable is: %s' %
943
# The guard should be PATH_FILE_H_, but we also allow PATH_FILE_H__
944
# for backward compatibility.
947
if ifndef != cppvar + '_':
950
error(filename, ifndef_linenum, 'build/header_guard', error_level,
951
'#ifndef header guard has wrong style, please use: %s' % cppvar)
953
if endif != ('#endif /* %s */' % cppvar):
955
if endif != ('#endif /* %s */' % (cppvar + '_')):
958
error(filename, endif_linenum, 'build/header_guard', error_level,
959
'#endif line should be "#endif /* %s */"' % cppvar)
962
def CheckForUnicodeReplacementCharacters(filename, lines, error):
963
"""Logs an error for each line containing Unicode replacement characters.
965
These indicate that either the file contained invalid UTF-8 (likely)
966
or Unicode replacement characters (which it shouldn't). Note that
967
it's possible for this to throw off line numbering if the invalid
968
UTF-8 occurred adjacent to a newline.
971
filename: The name of the current file.
972
lines: An array of strings, each representing a line of the file.
973
error: The function to call with any errors found.
975
for linenum, line in enumerate(lines):
976
if u'\ufffd' in line:
977
error(filename, linenum, 'readability/utf8', 5,
978
'Line contains invalid UTF-8 (or Unicode replacement character).')
981
def CheckForNewlineAtEOF(filename, lines, error):
982
"""Logs an error if there is no newline char at the end of the file.
985
filename: The name of the current file.
986
lines: An array of strings, each representing a line of the file.
987
error: The function to call with any errors found.
990
# The array lines() was created by adding two newlines to the
991
# original file (go figure), then splitting on \n.
992
# To verify that the file ends in \n, we just have to make sure the
993
# last-but-two element of lines() exists and is empty.
994
if len(lines) < 3 or lines[-2]:
995
error(filename, len(lines) - 2, 'whitespace/ending_newline', 5,
996
'Could not find a newline character at the end of the file.')
999
def CheckForMultilineCommentsAndStrings(filename, clean_lines, linenum, error):
1000
"""Logs an error if we see /* ... */ or "..." that extend past one line.
1002
/* ... */ comments are legit inside macros, for one line.
1003
Otherwise, we prefer // comments, so it's ok to warn about the
1004
other. Likewise, it's ok for strings to extend across multiple
1005
lines, as long as a line continuation character (backslash)
1006
terminates each line. Although not currently prohibited by the C++
1007
style guide, it's ugly and unnecessary. We don't do well with either
1008
in this lint program, so we warn about both.
1011
filename: The name of the current file.
1012
clean_lines: A CleansedLines instance containing the file.
1013
linenum: The number of the line to check.
1014
error: The function to call with any errors found.
1016
line = clean_lines.elided[linenum]
1018
# Remove all \\ (escaped backslashes) from the line. They are OK, and the
1019
# second (escaped) slash may trigger later \" detection erroneously.
1020
line = line.replace('\\\\', '')
1022
if line.count('/*') > line.count('*/'):
1023
error(filename, linenum, 'readability/multiline_comment', 5,
1024
'Complex multi-line /*...*/-style comment found. '
1025
'Lint may give bogus warnings. '
1026
'Consider replacing these with //-style comments, '
1027
'with #if 0...#endif, '
1028
'or with more clearly structured multi-line comments.')
1030
if (line.count('"') - line.count('\\"')) % 2:
1031
error(filename, linenum, 'readability/multiline_string', 5,
1032
'Multi-line string ("...") found. This lint script doesn\'t '
1033
'do well with such strings, and may give bogus warnings. They\'re '
1034
'ugly and unnecessary, and you should use concatenation instead".')
1038
('asctime(', 'asctime_r('),
1039
('ctime(', 'ctime_r('),
1040
('getgrgid(', 'getgrgid_r('),
1041
('getgrnam(', 'getgrnam_r('),
1042
('getlogin(', 'getlogin_r('),
1043
('getpwnam(', 'getpwnam_r('),
1044
('getpwuid(', 'getpwuid_r('),
1045
('gmtime(', 'gmtime_r('),
1046
('localtime(', 'localtime_r('),
1047
('rand(', 'rand_r('),
1048
('readdir(', 'readdir_r('),
1049
('strtok(', 'strtok_r('),
1050
('ttyname(', 'ttyname_r('),
1054
def CheckPosixThreading(filename, clean_lines, linenum, error):
1055
"""Checks for calls to thread-unsafe functions.
1057
Much code has been originally written without consideration of
1058
multi-threading. Also, engineers are relying on their old experience;
1059
they have learned posix before threading extensions were added. These
1060
tests guide the engineers to use thread-safe functions (when using
1064
filename: The name of the current file.
1065
clean_lines: A CleansedLines instance containing the file.
1066
linenum: The number of the line to check.
1067
error: The function to call with any errors found.
1069
line = clean_lines.elided[linenum]
1070
for single_thread_function, multithread_safe_function in threading_list:
1071
ix = line.find(single_thread_function)
1072
# Comparisons made explicit for clarity -- pylint: disable-msg=C6403
1073
if ix >= 0 and (ix == 0 or (not line[ix - 1].isalnum() and
1074
line[ix - 1] not in ('_', '.', '>'))):
1075
error(filename, linenum, 'runtime/threadsafe_fn', 2,
1076
'Consider using ' + multithread_safe_function +
1077
'...) instead of ' + single_thread_function +
1078
'...) for improved thread safety.')
1081
# Matches invalid increment: *count++, which moves pointer insead of
1082
# incrementing a value.
1083
_RE_PATTERN_IVALID_INCREMENT = re.compile(
1084
r'^\s*\*\w+(\+\+|--);')
1087
def CheckInvalidIncrement(filename, clean_lines, linenum, error):
1088
"""Checks for invalud increment *count++.
1090
For example following function:
1091
void increment_counter(int* count) {
1094
is invalid, because it effectively does count++, moving pointer, and should
1095
be replaced with ++*count, (*count)++ or *count += 1.
1098
filename: The name of the current file.
1099
clean_lines: A CleansedLines instance containing the file.
1100
linenum: The number of the line to check.
1101
error: The function to call with any errors found.
1103
line = clean_lines.elided[linenum]
1104
if _RE_PATTERN_IVALID_INCREMENT.match(line):
1105
error(filename, linenum, 'runtime/invalid_increment', 5,
1106
'Changing pointer instead of value (or unused value of operator*).')
1109
class _ClassInfo(object):
1110
"""Stores information about a class."""
1112
def __init__(self, name, linenum):
1114
self.linenum = linenum
1115
self.seen_open_brace = False
1116
self.is_derived = False
1117
self.virtual_method_linenumber = None
1118
self.has_virtual_destructor = False
1119
self.brace_depth = 0
1122
class _ClassState(object):
1123
"""Holds the current state of the parse relating to class declarations.
1125
It maintains a stack of _ClassInfos representing the parser's guess
1126
as to the current nesting of class declarations. The innermost class
1127
is at the top (back) of the stack. Typically, the stack will either
1128
be empty or have exactly one entry.
1132
self.classinfo_stack = []
1134
def CheckFinished(self, filename, error):
1135
"""Checks that all classes have been completely parsed.
1137
Call this when all lines in a file have been processed.
1139
filename: The name of the current file.
1140
error: The function to call with any errors found.
1142
if self.classinfo_stack:
1143
# Note: This test can result in false positives if #ifdef constructs
1144
# get in the way of brace matching. See the testBuildClass test in
1145
# cpplint_unittest.py for an example of this.
1146
error(filename, self.classinfo_stack[0].linenum, 'build/class', 5,
1147
'Failed to find complete declaration of class %s' %
1148
self.classinfo_stack[0].name)
1151
def CheckForNonStandardConstructs(filename, clean_lines, linenum,
1152
class_state, error):
1153
"""Logs an error if we see certain non-ANSI constructs ignored by gcc-2.
1155
Complain about several constructs which gcc-2 accepts, but which are
1156
not standard C++. Warning about these in lint is one way to ease the
1157
transition to new compilers.
1158
- put storage class first (e.g. "static const" instead of "const static").
1159
- "%lld" instead of %qd" in printf-type functions.
1160
- "%1$d" is non-standard in printf-type functions.
1161
- "\%" is an undefined character escape sequence.
1162
- text after #endif is not allowed.
1163
- invalid inner-style forward declaration.
1164
- >? and <? operators, and their >?= and <?= cousins.
1165
- classes with virtual methods need virtual destructors (compiler warning
1166
available, but not turned on yet.)
1168
Additionally, check for constructor/destructor style violations as it
1169
is very convenient to do so while checking for gcc-2 compliance.
1172
filename: The name of the current file.
1173
clean_lines: A CleansedLines instance containing the file.
1174
linenum: The number of the line to check.
1175
class_state: A _ClassState instance which maintains information about
1176
the current stack of nested class declarations being parsed.
1177
error: A callable to which errors are reported, which takes 4 arguments:
1178
filename, line number, error level, and message
1181
# Remove comments from the line, but leave in strings for now.
1182
line = clean_lines.lines[linenum]
1184
if Search(r'printf\s*\(.*".*%[-+ ]?\d*q', line):
1185
error(filename, linenum, 'runtime/printf_format', 3,
1186
'%q in format strings is deprecated. Use %ll instead.')
1188
if Search(r'printf\s*\(.*".*%\d+\$', line):
1189
error(filename, linenum, 'runtime/printf_format', 2,
1190
'%N$ formats are unconventional. Try rewriting to avoid them.')
1192
# Remove escaped backslashes before looking for undefined escapes.
1193
line = line.replace('\\\\', '')
1195
if Search(r'("|\').*\\(%|\[|\(|{)', line):
1196
error(filename, linenum, 'build/printf_format', 3,
1197
'%, [, (, and { are undefined character escapes. Unescape them.')
1199
# For the rest, work with both comments and strings removed.
1200
line = clean_lines.elided[linenum]
1202
if Search(r'\b(const|volatile|void|char|short|int|long'
1203
r'|float|double|signed|unsigned'
1204
r'|schar|u?int8|u?int16|u?int32|u?int64)'
1205
r'\s+(auto|register|static|extern|typedef)\b',
1207
error(filename, linenum, 'build/storage_class', 5,
1208
'Storage class (static, extern, typedef, etc) should be first.')
1210
if Match(r'\s*#\s*endif\s*[^/\s]+', line):
1211
error(filename, linenum, 'build/endif_comment', 5,
1212
'Uncommented text after #endif is non-standard. Use a comment.')
1214
if Match(r'\s*class\s+(\w+\s*::\s*)+\w+\s*;', line):
1215
error(filename, linenum, 'build/forward_decl', 5,
1216
'Inner-style forward declarations are invalid. Remove this line.')
1218
if Search(r'(\w+|[+-]?\d+(\.\d*)?)\s*(<|>)\?=?\s*(\w+|[+-]?\d+)(\.\d*)?',
1220
error(filename, linenum, 'build/deprecated', 3,
1221
'>? and <? (max and min) operators are non-standard and deprecated.')
1223
# Track class entry and exit, and attempt to find cases within the
1224
# class declaration that don't meet the C++ style
1225
# guidelines. Tracking is very dependent on the code matching Google
1226
# style guidelines, but it seems to perform well enough in testing
1227
# to be a worthwhile addition to the checks.
1228
classinfo_stack = class_state.classinfo_stack
1229
# Look for a class declaration
1230
class_decl_match = Match(
1231
r'\s*(template\s*<[\w\s<>,:]*>\s*)?(class|struct)\s+(\w+(::\w+)*)', line)
1232
if class_decl_match:
1233
classinfo_stack.append(_ClassInfo(class_decl_match.group(3), linenum))
1235
# Everything else in this function uses the top of the stack if it's
1237
if not classinfo_stack:
1240
classinfo = classinfo_stack[-1]
1242
# If the opening brace hasn't been seen look for it and also
1243
# parent class declarations.
1244
if not classinfo.seen_open_brace:
1245
# If the line has a ';' in it, assume it's a forward declaration or
1246
# a single-line class declaration, which we won't process.
1247
if line.find(';') != -1:
1248
classinfo_stack.pop()
1250
classinfo.seen_open_brace = (line.find('{') != -1)
1251
# Look for a bare ':'
1252
if Search('(^|[^:]):($|[^:])', line):
1253
classinfo.is_derived = True
1254
if not classinfo.seen_open_brace:
1255
return # Everything else in this function is for after open brace
1257
# The class may have been declared with namespace or classname qualifiers.
1258
# The constructor and destructor will not have those qualifiers.
1259
base_classname = classinfo.name.split('::')[-1]
1261
# Look for single-argument constructors that aren't marked explicit.
1262
# Technically a valid construct, but against style.
1263
args = Match(r'(?<!explicit)\s+%s\s*\(([^,()]+)\)'
1264
% re.escape(base_classname),
1267
args.group(1) != 'void' and
1268
not Match(r'(const\s+)?%s\s*&' % re.escape(base_classname),
1269
args.group(1).strip())):
1270
error(filename, linenum, 'runtime/explicit', 5,
1271
'Single-argument constructors should be marked explicit.')
1273
# Look for methods declared virtual.
1274
if Search(r'\bvirtual\b', line):
1275
classinfo.virtual_method_linenumber = linenum
1276
# Only look for a destructor declaration on the same line. It would
1277
# be extremely unlikely for the destructor declaration to occupy
1278
# more than one line.
1279
if Search(r'~%s\s*\(' % base_classname, line):
1280
classinfo.has_virtual_destructor = True
1282
# Look for class end.
1283
brace_depth = classinfo.brace_depth
1284
brace_depth = brace_depth + line.count('{') - line.count('}')
1285
if brace_depth <= 0:
1286
classinfo = classinfo_stack.pop()
1287
# Try to detect missing virtual destructor declarations.
1288
# For now, only warn if a non-derived class with virtual methods lacks
1289
# a virtual destructor. This is to make it less likely that people will
1290
# declare derived virtual destructors without declaring the base
1291
# destructor virtual.
1292
if ((classinfo.virtual_method_linenumber is not None) and
1293
(not classinfo.has_virtual_destructor) and
1294
(not classinfo.is_derived)): # Only warn for base classes
1295
error(filename, classinfo.linenum, 'runtime/virtual', 4,
1296
'The class %s probably needs a virtual destructor due to '
1297
'having virtual method(s), one declared at line %d.'
1298
% (classinfo.name, classinfo.virtual_method_linenumber))
1300
classinfo.brace_depth = brace_depth
1303
def CheckSpacingForFunctionCall(filename, line, linenum, error):
1304
"""Checks for the correctness of various spacing around function calls.
1307
filename: The name of the current file.
1308
line: The text of the line to check.
1309
linenum: The number of the line to check.
1310
error: The function to call with any errors found.
1313
# Since function calls often occur inside if/for/while/switch
1314
# expressions - which have their own, more liberal conventions - we
1315
# first see if we should be looking inside such an expression for a
1316
# function call, to which we can apply more strict standards.
1317
fncall = line # if there's no control flow construct, look at whole line
1318
for pattern in (r'\bif\s*\((.*)\)\s*{',
1319
r'\bfor\s*\((.*)\)\s*{',
1320
r'\bwhile\s*\((.*)\)\s*[{;]',
1321
r'\bswitch\s*\((.*)\)\s*{'):
1322
match = Search(pattern, line)
1324
fncall = match.group(1) # look inside the parens for function calls
1327
# Except in if/for/while/switch, there should never be space
1328
# immediately inside parens (eg "f( 3, 4 )"). We make an exception
1329
# for nested parens ( (a+b) + c ). Likewise, there should never be
1330
# a space before a ( when it's a function argument. I assume it's a
1331
# function argument when the char before the whitespace is legal in
1332
# a function name (alnum + _) and we're not starting a macro. Also ignore
1333
# pointers and references to arrays and functions coz they're too tricky:
1334
# we use a very simple way to recognize these:
1335
# " (something)(maybe-something)" or
1336
# " (something)(maybe-something," or
1337
# " (something)[something]"
1338
# Note that we assume the contents of [] to be short enough that
1339
# they'll never need to wrap.
1340
if ( # Ignore control structures.
1341
not Search(r'\b(if|for|while|switch|return|delete)\b', fncall) and
1342
# Ignore pointers/references to functions.
1343
not Search(r' \([^)]+\)\([^)]*(\)|,$)', fncall) and
1344
# Ignore pointers/references to arrays.
1345
not Search(r' \([^)]+\)\[[^\]]+\]', fncall)):
1346
if Search(r'\w\s*\(\s(?!\s*\\$)', fncall): # a ( used for a fn call
1347
error(filename, linenum, 'whitespace/parens', 4,
1348
'Extra space after ( in function call')
1349
elif Search(r'\(\s+(?!(\s*\\)|\()', fncall):
1350
error(filename, linenum, 'whitespace/parens', 2,
1351
'Extra space after (')
1352
if (Search(r'\w\s+\(', fncall) and
1353
not Search(r'#\s*define|typedef', fncall)):
1354
error(filename, linenum, 'whitespace/parens', 4,
1355
'Extra space before ( in function call')
1356
# If the ) is followed only by a newline or a { + newline, assume it's
1357
# part of a control statement (if/while/etc), and don't complain
1358
if Search(r'[^)]\s+\)\s*[^{\s]', fncall):
1359
error(filename, linenum, 'whitespace/parens', 2,
1360
'Extra space before )')
1363
def IsBlankLine(line):
1364
"""Returns true if the given line is blank.
1366
We consider a line to be blank if the line is empty or consists of
1370
line: A line of a string.
1373
True, if the given line is blank.
1375
return not line or line.isspace()
1378
def CheckForFunctionLengths(filename, clean_lines, linenum,
1379
function_state, error):
1380
"""Reports for long function bodies.
1382
For an overview why this is done, see:
1383
http://google-styleguide.googlecode.com/svn/trunk/cppguide.xml#Write_Short_Functions
1385
Uses a simplistic algorithm assuming other style guidelines
1386
(especially spacing) are followed.
1387
Only checks unindented functions, so class members are unchecked.
1388
Trivial bodies are unchecked, so constructors with huge initializer lists
1390
Blank/comment lines are not counted so as to avoid encouraging the removal
1391
of vertical space and commments just to get through a lint check.
1392
NOLINT *on the last line of a function* disables this check.
1395
filename: The name of the current file.
1396
clean_lines: A CleansedLines instance containing the file.
1397
linenum: The number of the line to check.
1398
function_state: Current function name and lines in body so far.
1399
error: The function to call with any errors found.
1401
lines = clean_lines.lines
1402
line = lines[linenum]
1403
raw = clean_lines.raw_lines
1404
raw_line = raw[linenum]
1407
starting_func = False
1408
regexp = r'(\w(\w|::|\*|\&|\s)*)\(' # decls * & space::name( ...
1409
match_result = Match(regexp, line)
1411
# If the name is all caps and underscores, figure it's a macro and
1412
# ignore it, unless it's TEST or TEST_F.
1413
function_name = match_result.group(1).split()[-1]
1414
if function_name == 'TEST' or function_name == 'TEST_F' or (
1415
not Match(r'[A-Z_]+$', function_name)):
1416
starting_func = True
1420
for start_linenum in xrange(linenum, clean_lines.NumLines()):
1421
start_line = lines[start_linenum]
1422
joined_line += ' ' + start_line.lstrip()
1423
if Search(r'(;|})', start_line): # Declarations and trivial functions
1426
elif Search(r'{', start_line):
1428
function = Search(r'((\w|:)*)\(', line).group(1)
1429
if Match(r'TEST', function): # Handle TEST... macros
1430
parameter_regexp = Search(r'(\(.*\))', joined_line)
1431
if parameter_regexp: # Ignore bad syntax
1432
function += parameter_regexp.group(1)
1435
function_state.Begin(function)
1438
# No body for the function (or evidence of a non-function) was found.
1439
error(filename, linenum, 'readability/fn_size', 5,
1440
'Lint failed to find start of function body.')
1441
elif Match(r'^\}\s*$', line): # function end
1442
if not Search(r'\bNOLINT\b', raw_line):
1443
function_state.Check(error, filename, linenum)
1444
function_state.End()
1445
elif not Match(r'^\s*$', line):
1446
function_state.Count() # Count non-blank/non-comment lines.
1449
_RE_PATTERN_TODO = re.compile(r'^//(\s*)TODO(\(.+?\))?:?(\s|$)?')
1452
def CheckComment(comment, filename, linenum, error):
1453
"""Checks for common mistakes in TODO comments.
1456
comment: The text of the comment from the line in question.
1457
filename: The name of the current file.
1458
linenum: The number of the line to check.
1459
error: The function to call with any errors found.
1461
match = _RE_PATTERN_TODO.match(comment)
1463
# One whitespace is correct; zero whitespace is handled elsewhere.
1464
leading_whitespace = match.group(1)
1465
if len(leading_whitespace) > 1:
1466
error(filename, linenum, 'whitespace/todo', 2,
1467
'Too many spaces before TODO')
1469
username = match.group(2)
1471
error(filename, linenum, 'readability/todo', 2,
1472
'Missing username in TODO; it should look like '
1473
'"// TODO(my_username): Stuff."')
1475
middle_whitespace = match.group(3)
1476
# Comparisons made explicit for correctness -- pylint: disable-msg=C6403
1477
if middle_whitespace != ' ' and middle_whitespace != '':
1478
error(filename, linenum, 'whitespace/todo', 2,
1479
'TODO(my_username) should be followed by a space')
1482
def CheckSpacing(filename, clean_lines, linenum, error):
1483
"""Checks for the correctness of various spacing issues in the code.
1485
Things we check for: spaces around operators, spaces after
1486
if/for/while/switch, no spaces around parens in function calls, two
1487
spaces between code and comment, don't start a block with a blank
1488
line, don't end a function with a blank line, don't have too many
1489
blank lines in a row.
1492
filename: The name of the current file.
1493
clean_lines: A CleansedLines instance containing the file.
1494
linenum: The number of the line to check.
1495
error: The function to call with any errors found.
1498
raw = clean_lines.raw_lines
1501
# Before nixing comments, check if the line is blank for no good
1502
# reason. This includes the first line after a block is opened, and
1503
# blank lines at the end of a function (ie, right before a line like '}'
1504
if IsBlankLine(line):
1505
elided = clean_lines.elided
1506
prev_line = elided[linenum - 1]
1507
prevbrace = prev_line.rfind('{')
1508
# TODO(unknown): Don't complain if line before blank line, and line after,
1509
# both start with alnums and are indented the same amount.
1510
# This ignores whitespace at the start of a namespace block
1511
# because those are not usually indented.
1512
if (prevbrace != -1 and prev_line[prevbrace:].find('}') == -1
1513
and prev_line[:prevbrace].find('namespace') == -1):
1514
# OK, we have a blank line at the start of a code block. Before we
1515
# complain, we check if it is an exception to the rule: The previous
1516
# non-empty line has the paramters of a function header that are indented
1517
# 4 spaces (because they did not fit in a 80 column line when placed on
1518
# the same line as the function name). We also check for the case where
1519
# the previous line is indented 6 spaces, which may happen when the
1520
# initializers of a constructor do not fit into a 80 column line.
1522
if Match(r' {6}\w', prev_line): # Initializer list?
1523
# We are looking for the opening column of initializer list, which
1524
# should be indented 4 spaces to cause 6 space indentation afterwards.
1525
search_position = linenum-2
1526
while (search_position >= 0
1527
and Match(r' {6}\w', elided[search_position])):
1528
search_position -= 1
1529
exception = (search_position >= 0
1530
and elided[search_position][:5] == ' :')
1532
# Search for the function arguments or an initializer list. We use a
1533
# simple heuristic here: If the line is indented 4 spaces; and we have a
1534
# closing paren, without the opening paren, followed by an opening brace
1535
# or colon (for initializer lists) we assume that it is the last line of
1536
# a function header. If we have a colon indented 4 spaces, it is an
1538
exception = (Match(r' {4}\w[^\(]*\)\s*(const\s*)?(\{\s*$|:)',
1540
or Match(r' {4}:', prev_line))
1543
error(filename, linenum, 'whitespace/blank_line', 2,
1544
'Blank line at the start of a code block. Is this needed?')
1545
# This doesn't ignore whitespace at the end of a namespace block
1546
# because that is too hard without pairing open/close braces;
1547
# however, a special exception is made for namespace closing
1548
# brackets which have a comment containing "namespace".
1550
# Also, ignore blank lines at the end of a block in a long if-else
1553
# // Something followed by a blank line
1555
# } else if (condition2) {
1558
if linenum + 1 < clean_lines.NumLines():
1559
next_line = raw[linenum + 1]
1561
and Match(r'\s*}', next_line)
1562
and next_line.find('namespace') == -1
1563
and next_line.find('} else ') == -1):
1564
error(filename, linenum, 'whitespace/blank_line', 3,
1565
'Blank line at the end of a code block. Is this needed?')
1567
# Next, we complain if there's a comment too near the text
1568
commentpos = line.find('//')
1569
if commentpos != -1:
1570
# Check if the // may be in quotes. If so, ignore it
1571
# Comparisons made explicit for clarity -- pylint: disable-msg=C6403
1572
if (line.count('"', 0, commentpos) -
1573
line.count('\\"', 0, commentpos)) % 2 == 0: # not in quotes
1574
# Allow one space for new scopes, two spaces otherwise:
1575
if (not Match(r'^\s*{ //', line) and
1576
((commentpos >= 1 and
1577
line[commentpos-1] not in string.whitespace) or
1578
(commentpos >= 2 and
1579
line[commentpos-2] not in string.whitespace))):
1580
error(filename, linenum, 'whitespace/comments', 2,
1581
'At least two spaces is best between code and comments')
1582
# There should always be a space between the // and the comment
1583
commentend = commentpos + 2
1584
if commentend < len(line) and not line[commentend] == ' ':
1585
# but some lines are exceptions -- e.g. if they're big
1586
# comment delimiters like:
1587
# //----------------------------------------------------------
1588
# or they begin with multiple slashes followed by a space:
1589
# //////// Header comment
1590
match = (Search(r'[=/-]{4,}\s*$', line[commentend:]) or
1591
Search(r'^/+ ', line[commentend:]))
1593
error(filename, linenum, 'whitespace/comments', 4,
1594
'Should have a space between // and comment')
1595
CheckComment(line[commentpos:], filename, linenum, error)
1597
line = clean_lines.elided[linenum] # get rid of comments and strings
1599
# Don't try to do spacing checks for operator methods
1600
line = re.sub(r'operator(==|!=|<|<<|<=|>=|>>|>)\(', 'operator\(', line)
1602
# = should have no space before and should always have a space after.
1603
if Search(r'[\s.]=[^=]', line):
1604
error(filename, linenum, 'whitespace/operators', 4,
1605
'Space found before =')
1606
if Search(r'=[\w.]', line):
1607
error(filename, linenum, 'whitespace/operators', 4,
1608
'Missing space after =')
1610
# It's ok not to have spaces around binary operators like + - * /, but if
1611
# there's too little whitespace, we get concerned. It's hard to tell,
1612
# though, so we punt on this one for now. TODO.
1614
# You should always have whitespace around binary operators.
1615
# Alas, we can't test < or > because they're legitimately used sans spaces
1616
# (a->b, vector<int> a). The only time we can tell is a < with no >, and
1617
# only if it's not template params list spilling into the next line.
1618
match = Search(r'[^<>=!\s](==|!=|<=|>=)[^<>=!\s]', line)
1620
# Note that while it seems that the '<[^<]*' term in the following
1621
# regexp could be simplified to '<.*', which would indeed match
1622
# the same class of strings, the [^<] means that searching for the
1623
# regexp takes linear rather than quadratic time.
1624
if not Search(r'<[^<]*,\s*$', line): # template params spill
1625
match = Search(r'[^<>=!\s](<)[^<>=!\s]([^>]|->)*$', line)
1627
error(filename, linenum, 'whitespace/operators', 3,
1628
'Missing spaces around %s' % match.group(1))
1629
# We allow no-spaces around << and >> when used like this: 10<<20, but
1630
# not otherwise (particularly, not when used as streams)
1631
match = Search(r'[^0-9\s](<<|>>)[^0-9\s]', line)
1633
error(filename, linenum, 'whitespace/operators', 3,
1634
'Missing spaces around %s' % match.group(1))
1636
# There shouldn't be space around unary operators
1637
match = Search(r'(!\s|~\s|[\s]--[\s;]|[\s]\+\+[\s;])', line)
1639
error(filename, linenum, 'whitespace/operators', 4,
1640
'Extra space for operator %s' % match.group(1))
1642
# A pet peeve of mine: no spaces after an if, while, switch, or for
1643
match = Search(r' (if\(|for\(|while\(|switch\()', line)
1645
error(filename, linenum, 'whitespace/parens', 5,
1646
'Missing space before ( in %s' % match.group(1))
1648
# For if/for/while/switch, the left and right parens should be
1649
# consistent about how many spaces are inside the parens, and
1650
# there should either be zero or one spaces inside the parens.
1651
# We don't want: "if ( foo)" or "if ( foo )".
1652
# Exception: "for ( ; foo; bar)" and "for (foo; bar; )" are allowed.
1653
match = Search(r'\b(if|for|while|switch)\s*'
1654
r'\(([ ]*)(.).*[^ ]+([ ]*)\)\s*{\s*$',
1657
if len(match.group(2)) != len(match.group(4)):
1658
if not (match.group(3) == ';' and
1659
len(match.group(2)) == 1 + len(match.group(4)) or
1660
not match.group(2) and Search(r'\bfor\s*\(.*; \)', line)):
1661
error(filename, linenum, 'whitespace/parens', 5,
1662
'Mismatching spaces inside () in %s' % match.group(1))
1663
if not len(match.group(2)) in [0, 1]:
1664
error(filename, linenum, 'whitespace/parens', 5,
1665
'Should have zero or one spaces inside ( and ) in %s' %
1668
# You should always have a space after a comma (either as fn arg or operator)
1669
if Search(r',[^\s]', line):
1670
error(filename, linenum, 'whitespace/comma', 3,
1671
'Missing space after ,')
1673
# Next we will look for issues with function calls.
1674
CheckSpacingForFunctionCall(filename, line, linenum, error)
1676
# Except after an opening paren, you should have spaces before your braces.
1677
# And since you should never have braces at the beginning of a line, this is
1679
if Search(r'[^ (]{', line):
1680
error(filename, linenum, 'whitespace/braces', 5,
1681
'Missing space before {')
1683
# Make sure '} else {' has spaces.
1684
if Search(r'}else', line):
1685
error(filename, linenum, 'whitespace/braces', 5,
1686
'Missing space before else')
1688
# You shouldn't have spaces before your brackets, except maybe after
1689
# 'delete []' or 'new char * []'.
1690
if Search(r'\w\s+\[', line) and not Search(r'delete\s+\[', line):
1691
error(filename, linenum, 'whitespace/braces', 5,
1692
'Extra space before [')
1694
# You shouldn't have a space before a semicolon at the end of the line.
1695
# There's a special case for "for" since the style guide allows space before
1696
# the semicolon there.
1697
if Search(r':\s*;\s*$', line):
1698
error(filename, linenum, 'whitespace/semicolon', 5,
1699
'Semicolon defining empty statement. Use { } instead.')
1700
elif Search(r'^\s*;\s*$', line):
1701
error(filename, linenum, 'whitespace/semicolon', 5,
1702
'Line contains only semicolon. If this should be an empty statement, '
1704
elif (Search(r'\s+;\s*$', line) and
1705
not Search(r'\bfor\b', line)):
1706
error(filename, linenum, 'whitespace/semicolon', 5,
1707
'Extra space before last semicolon. If this should be an empty '
1708
'statement, use { } instead.')
1711
def GetPreviousNonBlankLine(clean_lines, linenum):
1712
"""Return the most recent non-blank line and its line number.
1715
clean_lines: A CleansedLines instance containing the file contents.
1716
linenum: The number of the line to check.
1719
A tuple with two elements. The first element is the contents of the last
1720
non-blank line before the current line, or the empty string if this is the
1721
first non-blank line. The second is the line number of that line, or -1
1722
if this is the first non-blank line.
1725
prevlinenum = linenum - 1
1726
while prevlinenum >= 0:
1727
prevline = clean_lines.elided[prevlinenum]
1728
if not IsBlankLine(prevline): # if not a blank line...
1729
return (prevline, prevlinenum)
1734
def CheckBraces(filename, clean_lines, linenum, error):
1735
"""Looks for misplaced braces (e.g. at the end of line).
1738
filename: The name of the current file.
1739
clean_lines: A CleansedLines instance containing the file.
1740
linenum: The number of the line to check.
1741
error: The function to call with any errors found.
1744
line = clean_lines.elided[linenum] # get rid of comments and strings
1746
if Match(r'\s*{\s*$', line):
1747
# We allow an open brace to start a line in the case where someone
1748
# is using braces in a block to explicitly create a new scope,
1749
# which is commonly used to control the lifetime of
1750
# stack-allocated variables. We don't detect this perfectly: we
1751
# just don't complain if the last non-whitespace character on the
1752
# previous non-blank line is ';', ':', '{', or '}'.
1753
prevline = GetPreviousNonBlankLine(clean_lines, linenum)[0]
1754
if not Search(r'[;:}{]\s*$', prevline):
1755
error(filename, linenum, 'whitespace/braces', 4,
1756
'{ should almost always be at the end of the previous line')
1758
# An else clause should be on the same line as the preceding closing brace.
1759
if Match(r'\s*else\s*', line):
1760
prevline = GetPreviousNonBlankLine(clean_lines, linenum)[0]
1761
if Match(r'\s*}\s*$', prevline):
1762
error(filename, linenum, 'whitespace/newline', 4,
1763
'An else should appear on the same line as the preceding }')
1765
# If braces come on one side of an else, they should be on both.
1766
# However, we have to worry about "else if" that spans multiple lines!
1767
if Search(r'}\s*else[^{]*$', line) or Match(r'[^}]*else\s*{', line):
1768
if Search(r'}\s*else if([^{]*)$', line): # could be multi-line if
1769
# find the ( after the if
1770
pos = line.find('else if')
1771
pos = line.find('(', pos)
1773
(endline, _, endpos) = CloseExpression(clean_lines, linenum, pos)
1774
if endline[endpos:].find('{') == -1: # must be brace after if
1775
error(filename, linenum, 'readability/braces', 5,
1776
'If an else has a brace on one side, it should have it on both')
1777
else: # common case: else not followed by a multi-line if
1778
error(filename, linenum, 'readability/braces', 5,
1779
'If an else has a brace on one side, it should have it on both')
1781
# Likewise, an else should never have the else clause on the same line
1782
if Search(r'\belse [^\s{]', line) and not Search(r'\belse if\b', line):
1783
error(filename, linenum, 'whitespace/newline', 4,
1784
'Else clause should never be on same line as else (use 2 lines)')
1786
# In the same way, a do/while should never be on one line
1787
if Match(r'\s*do [^\s{]', line):
1788
error(filename, linenum, 'whitespace/newline', 4,
1789
'do/while clauses should not be on a single line')
1791
# Braces shouldn't be followed by a ; unless they're defining a struct
1792
# or initializing an array.
1793
# We can't tell in general, but we can for some common cases.
1794
prevlinenum = linenum
1796
(prevline, prevlinenum) = GetPreviousNonBlankLine(clean_lines, prevlinenum)
1797
if Match(r'\s+{.*}\s*;', line) and not prevline.count(';'):
1798
line = prevline + line
1801
if (Search(r'{.*}\s*;', line) and
1802
line.count('{') == line.count('}') and
1803
not Search(r'struct|class|enum|\s*=\s*{', line)):
1804
error(filename, linenum, 'readability/braces', 4,
1805
"You don't need a ; after a }")
1808
def ReplaceableCheck(operator, macro, line):
1809
"""Determine whether a basic CHECK can be replaced with a more specific one.
1811
For example suggest using CHECK_EQ instead of CHECK(a == b) and
1812
similarly for CHECK_GE, CHECK_GT, CHECK_LE, CHECK_LT, CHECK_NE.
1815
operator: The C++ operator used in the CHECK.
1816
macro: The CHECK or EXPECT macro being called.
1817
line: The current source line.
1820
True if the CHECK can be replaced with a more specific one.
1823
# This matches decimal and hex integers, strings, and chars (in that order).
1824
match_constant = r'([-+]?(\d+|0[xX][0-9a-fA-F]+)[lLuU]{0,3}|".*"|\'.*\')'
1826
# Expression to match two sides of the operator with something that
1827
# looks like a literal, since CHECK(x == iterator) won't compile.
1828
# This means we can't catch all the cases where a more specific
1829
# CHECK is possible, but it's less annoying than dealing with
1830
# extraneous warnings.
1831
match_this = (r'\s*' + macro + r'\((\s*' +
1832
match_constant + r'\s*' + operator + r'[^<>].*|'
1833
r'.*[^<>]' + operator + r'\s*' + match_constant +
1836
# Don't complain about CHECK(x == NULL) or similar because
1837
# CHECK_EQ(x, NULL) won't compile (requires a cast).
1838
# Also, don't complain about more complex boolean expressions
1839
# involving && or || such as CHECK(a == b || c == d).
1840
return Match(match_this, line) and not Search(r'NULL|&&|\|\|', line)
1843
def CheckCheck(filename, clean_lines, linenum, error):
1844
"""Checks the use of CHECK and EXPECT macros.
1847
filename: The name of the current file.
1848
clean_lines: A CleansedLines instance containing the file.
1849
linenum: The number of the line to check.
1850
error: The function to call with any errors found.
1853
# Decide the set of replacement macros that should be suggested
1854
raw_lines = clean_lines.raw_lines
1856
for macro in _CHECK_MACROS:
1857
if raw_lines[linenum].find(macro) >= 0:
1858
current_macro = macro
1860
if not current_macro:
1861
# Don't waste time here if line doesn't contain 'CHECK' or 'EXPECT'
1864
line = clean_lines.elided[linenum] # get rid of comments and strings
1866
# Encourage replacing plain CHECKs with CHECK_EQ/CHECK_NE/etc.
1867
for operator in ['==', '!=', '>=', '>', '<=', '<']:
1868
if ReplaceableCheck(operator, current_macro, line):
1869
error(filename, linenum, 'readability/check', 2,
1870
'Consider using %s instead of %s(a %s b)' % (
1871
_CHECK_REPLACEMENT[current_macro][operator],
1872
current_macro, operator))
1876
def GetLineWidth(line):
1877
"""Determines the width of the line in column positions.
1880
line: A string, which may be a Unicode string.
1883
The width of the line in column positions, accounting for Unicode
1884
combining characters and wide characters.
1886
if isinstance(line, unicode):
1888
for c in unicodedata.normalize('NFC', line):
1889
if unicodedata.east_asian_width(c) in ('W', 'F'):
1891
elif not unicodedata.combining(c):
1898
def CheckStyle(filename, clean_lines, linenum, file_extension, error):
1899
"""Checks rules from the 'C++ style rules' section of cppguide.html.
1901
Most of these rules are hard to test (naming, comment style), but we
1902
do what we can. In particular we check for 2-space indents, line lengths,
1903
tab usage, spaces inside code, etc.
1906
filename: The name of the current file.
1907
clean_lines: A CleansedLines instance containing the file.
1908
linenum: The number of the line to check.
1909
file_extension: The extension (without the dot) of the filename.
1910
error: The function to call with any errors found.
1913
raw_lines = clean_lines.raw_lines
1914
line = raw_lines[linenum]
1916
if line.find('\t') != -1:
1917
error(filename, linenum, 'whitespace/tab', 1,
1918
'Tab found; better to use spaces')
1920
# One or three blank spaces at the beginning of the line is weird; it's
1921
# hard to reconcile that with 2-space indents.
1922
# NOTE: here are the conditions rob pike used for his tests. Mine aren't
1923
# as sophisticated, but it may be worth becoming so: RLENGTH==initial_spaces
1924
# if(RLENGTH > 20) complain = 0;
1925
# if(match($0, " +(error|private|public|protected):")) complain = 0;
1926
# if(match(prev, "&& *$")) complain = 0;
1927
# if(match(prev, "\\|\\| *$")) complain = 0;
1928
# if(match(prev, "[\",=><] *$")) complain = 0;
1929
# if(match($0, " <<")) complain = 0;
1930
# if(match(prev, " +for \\(")) complain = 0;
1931
# if(prevodd && match(prevprev, " +for \\(")) complain = 0;
1933
cleansed_line = clean_lines.elided[linenum]
1934
while initial_spaces < len(line) and line[initial_spaces] == ' ':
1936
if line and line[-1].isspace():
1937
error(filename, linenum, 'whitespace/end_of_line', 4,
1938
'Line ends in whitespace. Consider deleting these extra spaces.')
1939
# There are certain situations we allow one space, notably for labels
1940
elif ((initial_spaces == 1 or initial_spaces == 3) and
1941
not Match(r'\s*\w+\s*:\s*$', cleansed_line)):
1942
error(filename, linenum, 'whitespace/indent', 3,
1943
'Weird number of spaces at line-start. '
1944
'Are you using a 2-space indent?')
1945
# Labels should always be indented at least one space.
1946
elif not initial_spaces and line[:2] != '//' and Search(r'[^:]:\s*$',
1948
error(filename, linenum, 'whitespace/labels', 4,
1949
'Labels should always be indented at least one space. '
1950
'If this is a member-initializer list in a constructor, '
1951
'the colon should be on the line after the definition header.')
1953
# Check if the line is a header guard.
1954
is_header_guard = False
1955
if file_extension == 'h':
1956
cppvar = GetHeaderGuardCPPVariable(filename)
1957
if (line.startswith('#ifndef %s' % cppvar) or
1958
line.startswith('#define %s' % cppvar) or
1959
line.startswith('#endif // %s' % cppvar)):
1960
is_header_guard = True
1961
# #include lines and header guards can be long, since there's no clean way to
1964
# URLs can be long too. It's possible to split these, but it makes them
1965
# harder to cut&paste.
1966
if (not line.startswith('#include') and not is_header_guard and
1967
not Match(r'^\s*//.*http(s?)://\S*$', line)):
1968
line_width = GetLineWidth(line)
1969
if line_width > 100:
1970
error(filename, linenum, 'whitespace/line_length', 4,
1971
'Lines should very rarely be longer than 100 characters')
1972
elif line_width > 80:
1973
error(filename, linenum, 'whitespace/line_length', 2,
1974
'Lines should be <= 80 characters long')
1976
if (cleansed_line.count(';') > 1 and
1977
# for loops are allowed two ;'s (and may run over two lines).
1978
cleansed_line.find('for') == -1 and
1979
(GetPreviousNonBlankLine(clean_lines, linenum)[0].find('for') == -1 or
1980
GetPreviousNonBlankLine(clean_lines, linenum)[0].find(';') != -1) and
1981
# It's ok to have many commands in a switch case that fits in 1 line
1982
not ((cleansed_line.find('case ') != -1 or
1983
cleansed_line.find('default:') != -1) and
1984
cleansed_line.find('break;') != -1)):
1985
error(filename, linenum, 'whitespace/newline', 4,
1986
'More than one command on the same line')
1988
# Some more style checks
1989
CheckBraces(filename, clean_lines, linenum, error)
1990
CheckSpacing(filename, clean_lines, linenum, error)
1991
CheckCheck(filename, clean_lines, linenum, error)
1994
_RE_PATTERN_INCLUDE_NEW_STYLE = re.compile(r'#include +"[^/]+\.h"')
1995
_RE_PATTERN_INCLUDE = re.compile(r'^\s*#\s*include\s*([<"])([^>"]*)[>"].*$')
1996
# Matches the first component of a filename delimited by -s and _s. That is:
1997
# _RE_FIRST_COMPONENT.match('foo').group(0) == 'foo'
1998
# _RE_FIRST_COMPONENT.match('foo.cc').group(0) == 'foo'
1999
# _RE_FIRST_COMPONENT.match('foo-bar_baz.cc').group(0) == 'foo'
2000
# _RE_FIRST_COMPONENT.match('foo_bar-baz.cc').group(0) == 'foo'
2001
_RE_FIRST_COMPONENT = re.compile(r'^[^-_.]+')
2004
def _DropCommonSuffixes(filename):
2005
"""Drops common suffixes like _test.cc or -inl.h from filename.
2008
>>> _DropCommonSuffixes('foo/foo-inl.h')
2010
>>> _DropCommonSuffixes('foo/bar/foo.cc')
2012
>>> _DropCommonSuffixes('foo/foo_internal.h')
2014
>>> _DropCommonSuffixes('foo/foo_unusualinternal.h')
2015
'foo/foo_unusualinternal'
2018
filename: The input filename.
2021
The filename with the common suffix removed.
2023
for suffix in ('test.cc', 'regtest.cc', 'unittest.cc',
2024
'inl.h', 'impl.h', 'internal.h'):
2025
if (filename.endswith(suffix) and len(filename) > len(suffix) and
2026
filename[-len(suffix) - 1] in ('-', '_')):
2027
return filename[:-len(suffix) - 1]
2028
return os.path.splitext(filename)[0]
2031
def _IsTestFilename(filename):
2032
"""Determines if the given filename has a suffix that identifies it as a test.
2035
filename: The input filename.
2038
True if 'filename' looks like a test, False otherwise.
2040
if (filename.endswith('_test.cc') or
2041
filename.endswith('_unittest.cc') or
2042
filename.endswith('_regtest.cc')):
2048
def _ClassifyInclude(fileinfo, include, is_system):
2049
"""Figures out what kind of header 'include' is.
2052
fileinfo: The current file cpplint is running over. A FileInfo instance.
2053
include: The path to a #included file.
2054
is_system: True if the #include used <> rather than "".
2057
One of the _XXX_HEADER constants.
2060
>>> _ClassifyInclude(FileInfo('foo/foo.cc'), 'stdio.h', True)
2062
>>> _ClassifyInclude(FileInfo('foo/foo.cc'), 'string', True)
2064
>>> _ClassifyInclude(FileInfo('foo/foo.cc'), 'foo/foo.h', False)
2066
>>> _ClassifyInclude(FileInfo('foo/foo_unknown_extension.cc'),
2067
... 'bar/foo_other_ext.h', False)
2069
>>> _ClassifyInclude(FileInfo('foo/foo.cc'), 'foo/bar.h', False)
2072
# This is a list of all standard c++ header files, except
2073
# those already checked for above.
2074
is_stl_h = include in _STL_HEADERS
2075
is_cpp_h = is_stl_h or include in _CPP_HEADERS
2079
return _CPP_SYS_HEADER
2081
return _C_SYS_HEADER
2083
# If the target file and the include we're checking share a
2084
# basename when we drop common extensions, and the include
2085
# lives in . , then it's likely to be owned by the target file.
2086
target_dir, target_base = (
2087
os.path.split(_DropCommonSuffixes(fileinfo.RepositoryName())))
2088
include_dir, include_base = os.path.split(_DropCommonSuffixes(include))
2089
if target_base == include_base and (
2090
include_dir == target_dir or
2091
include_dir == os.path.normpath(target_dir + '/../public')):
2092
return _LIKELY_MY_HEADER
2094
# If the target and include share some initial basename
2095
# component, it's possible the target is implementing the
2096
# include, so it's allowed to be first, but we'll never
2097
# complain if it's not there.
2098
target_first_component = _RE_FIRST_COMPONENT.match(target_base)
2099
include_first_component = _RE_FIRST_COMPONENT.match(include_base)
2100
if (target_first_component and include_first_component and
2101
target_first_component.group(0) ==
2102
include_first_component.group(0)):
2103
return _POSSIBLE_MY_HEADER
2105
return _OTHER_HEADER
2109
def CheckGlobalInclude(filename, clean_lines, linenum, include_state, error):
2110
"""Check rules that are applicable to #include lines.
2112
config.h should NEVER be included in headers
2113
unless those headers end in _priv and therefore are private headers.
2116
filename: The name of the current file.
2117
clean_lines: A CleansedLines instance containing the file.
2118
linenum: The number of the line to check.
2119
include_state: An _IncludeState instance in which the headers are inserted.
2120
error: The function to call with any errors found.
2122
if filename.endswith("config.h") or filename.endswith("_priv.h") or not filename.endswith(".h"):
2125
fileinfo = FileInfo(filename)
2127
line = clean_lines.lines[linenum]
2129
match = _RE_PATTERN_INCLUDE.search(line)
2131
include = match.group(2)
2132
if Match(r'(config|global|server_includes|_priv)\.h$', include):
2133
error(filename, linenum, 'build/include_config', 4,
2134
'Do not include config.h or files that include config.h in .h files')
2136
def CheckIncludeLine(filename, clean_lines, linenum, include_state, error):
2137
"""Check rules that are applicable to #include lines.
2139
Strings on #include lines are NOT removed from elided line, to make
2140
certain tasks easier. However, to prevent false positives, checks
2141
applicable to #include lines in CheckLanguage must be put here.
2144
filename: The name of the current file.
2145
clean_lines: A CleansedLines instance containing the file.
2146
linenum: The number of the line to check.
2147
include_state: An _IncludeState instance in which the headers are inserted.
2148
error: The function to call with any errors found.
2150
fileinfo = FileInfo(filename)
2152
line = clean_lines.lines[linenum]
2154
# "include" should use the new style "foo/bar.h" instead of just "bar.h"
2155
if _RE_PATTERN_INCLUDE_NEW_STYLE.search(line):
2156
error(filename, linenum, 'build/include', 4,
2157
'Include the directory when naming .h files')
2159
# we shouldn't include a file more than once. actually, there are a
2160
# handful of instances where doing so is okay, but in general it's
2162
match = _RE_PATTERN_INCLUDE.search(line)
2164
include = match.group(2)
2165
is_system = (match.group(1) == '<')
2166
if include in include_state:
2167
error(filename, linenum, 'build/include', 4,
2168
'"%s" already included at %s:%s' %
2169
(include, filename, include_state[include]))
2171
include_state[include] = linenum
2173
# We want to ensure that headers appear in the right order:
2174
# 1) for foo.cc, foo.h (preferred location)
2176
# 3) cpp system files
2177
# 4) for foo.cc, foo.h (deprecated location)
2178
# 5) other google headers
2180
# We classify each include statement as one of those 5 types
2181
# using a number of techniques. The include_state object keeps
2182
# track of the highest type seen, and complains if we see a
2183
# lower type after that.
2184
error_message = include_state.CheckNextIncludeOrder(
2185
_ClassifyInclude(fileinfo, include, is_system))
2187
error(filename, linenum, 'build/include_order', 4,
2188
'%s. Should be: %s.h, c system, c++ system, other.' %
2189
(error_message, fileinfo.BaseName()))
2191
# Look for any of the stream classes that are part of standard C++.
2192
match = _RE_PATTERN_INCLUDE.match(line)
2194
include = match.group(2)
2195
if Match(r'(f|ind|io|i|o|parse|pf|stdio|str|)?stream$', include):
2196
# Many unit tests use cout, so we exempt them.
2197
if not _IsTestFilename(filename):
2198
error(filename, linenum, 'readability/streams', 3,
2199
'Streams are highly discouraged.')
2201
def CheckLanguage(filename, clean_lines, linenum, file_extension, include_state,
2203
"""Checks rules from the 'C++ language rules' section of cppguide.html.
2205
Some of these rules are hard to test (function overloading, using
2206
uint32 inappropriately), but we do the best we can.
2209
filename: The name of the current file.
2210
clean_lines: A CleansedLines instance containing the file.
2211
linenum: The number of the line to check.
2212
file_extension: The extension (without the dot) of the filename.
2213
include_state: An _IncludeState instance in which the headers are inserted.
2214
error: The function to call with any errors found.
2216
# If the line is empty or consists of entirely a comment, no need to
2218
line = clean_lines.elided[linenum]
2222
match = _RE_PATTERN_INCLUDE.search(line)
2224
CheckIncludeLine(filename, clean_lines, linenum, include_state, error)
2225
CheckGlobalInclude(filename, clean_lines, linenum, include_state, error)
2228
# Create an extended_line, which is the concatenation of the current and
2229
# next lines, for more effective checking of code that may span more than one
2231
if linenum + 1 < clean_lines.NumLines():
2232
extended_line = line + clean_lines.elided[linenum + 1]
2234
extended_line = line
2236
# Make Windows paths like Unix.
2237
fullname = os.path.abspath(filename).replace('\\', '/')
2239
# TODO(unknown): figure out if they're using default arguments in fn proto.
2241
# Check to see if they're using an conversion function cast.
2242
# I just try to capture the most common basic types, though there are more.
2243
# Parameterless conversion functions, such as bool(), are allowed as they are
2244
# probably a member operator declaration or default constructor.
2246
r'\b(int|float|double|bool|char|int32|uint32|int64|uint64)\([^)]', line)
2248
# gMock methods are defined using some variant of MOCK_METHODx(name, type)
2249
# where type may be float(), int(string), etc. Without context they are
2250
# virtually indistinguishable from int(x) casts.
2251
if not Match(r'^\s*MOCK_(CONST_)?METHOD\d+(_T)?\(', line):
2252
error(filename, linenum, 'readability/casting', 4,
2253
'Using deprecated casting style. '
2254
'Use static_cast<%s>(...) instead' %
2257
CheckCStyleCast(filename, linenum, line, clean_lines.raw_lines[linenum],
2259
r'\((int|float|double|bool|char|u?int(16|32|64))\)',
2261
# This doesn't catch all cases. Consider (const char * const)"hello".
2262
CheckCStyleCast(filename, linenum, line, clean_lines.raw_lines[linenum],
2263
'reinterpret_cast', r'\((\w+\s?\*+\s?)\)', error)
2265
# In addition, we look for people taking the address of a cast. This
2266
# is dangerous -- casts can assign to temporaries, so the pointer doesn't
2267
# point where you think.
2269
r'(&\([^)]+\)[\w(])|(&(static|dynamic|reinterpret)_cast\b)', line):
2270
error(filename, linenum, 'runtime/casting', 4,
2271
('Are you taking an address of a cast? '
2272
'This is dangerous: could be a temp var. '
2273
'Take the address before doing the cast, rather than after'))
2275
# Check for people declaring static/global STL strings at the top level.
2276
# This is dangerous because the C++ language does not guarantee that
2277
# globals with constructors are initialized before the first access.
2279
r'((?:|static +)(?:|const +))string +([a-zA-Z0-9_:]+)\b(.*)',
2281
# Make sure it's not a function.
2282
# Function template specialization looks like: "string foo<Type>(...".
2283
# Class template definitions look like: "string Foo<Type>::Method(...".
2284
if match and not Match(r'\s*(<.*>)?(::[a-zA-Z0-9_]+)?\s*\(([^"]|$)',
2286
error(filename, linenum, 'runtime/string', 4,
2287
'For a static/global string constant, use a C style string instead: '
2289
(match.group(1), match.group(2)))
2291
# Check that we're not using RTTI outside of testing code.
2292
if Search(r'\bdynamic_cast<', line) and not _IsTestFilename(filename):
2293
error(filename, linenum, 'runtime/rtti', 5,
2294
'Do not use dynamic_cast<>. If you need to cast within a class '
2295
"hierarchy, use static_cast<> to upcast. Google doesn't support "
2298
if Search(r'\b([A-Za-z0-9_]*_)\(\1\)', line):
2299
error(filename, linenum, 'runtime/init', 4,
2300
'You seem to be initializing a member variable with itself.')
2302
if file_extension == 'h':
2303
# TODO(unknown): check that 1-arg constructors are explicit.
2304
# How to tell it's a constructor?
2305
# (handled in CheckForNonStandardConstructs for now)
2306
# TODO(unknown): check that classes have DISALLOW_EVIL_CONSTRUCTORS
2310
# Check if people are using the verboten C basic types. The only exception
2311
# we regularly allow is "unsigned short port" for port.
2312
if Search(r'\bshort port\b', line):
2313
if not Search(r'\bunsigned short port\b', line):
2314
error(filename, linenum, 'runtime/int', 4,
2315
'Use "unsigned short" for ports, not "short"')
2317
match = Search(r'\b(short|long(?! +double)|long long)\b', line)
2319
error(filename, linenum, 'runtime/int', 4,
2320
'Use int16/int64/etc, rather than the C type %s' % match.group(1))
2322
# When snprintf is used, the second argument shouldn't be a literal.
2323
match = Search(r'snprintf\s*\(([^,]*),\s*([0-9]*)\s*,', line)
2325
error(filename, linenum, 'runtime/printf', 3,
2326
'If you can, use sizeof(%s) instead of %s as the 2nd arg '
2327
'to snprintf.' % (match.group(1), match.group(2)))
2329
# Check if some verboten C functions are being used.
2330
if Search(r'\bsprintf\b', line):
2331
error(filename, linenum, 'runtime/printf', 5,
2332
'Never use sprintf. Use snprintf instead.')
2333
match = Search(r'\b(strcpy|strcat)\b', line)
2335
error(filename, linenum, 'runtime/printf', 4,
2336
'Almost always, snprintf is better than %s' % match.group(1))
2338
if Search(r'\bsscanf\b', line):
2339
error(filename, linenum, 'runtime/printf', 1,
2340
'sscanf can be ok, but is slow and can overflow buffers.')
2342
# Check for suspicious usage of "if" like
2344
if Search(r'\}\s*if\s*\(', line):
2345
error(filename, linenum, 'readability/braces', 4,
2346
'Did you mean "else if"? If not, start a new line for "if".')
2348
# Check for potential format string bugs like printf(foo).
2349
# We constrain the pattern not to pick things like DocidForPrintf(foo).
2350
# Not perfect but it can catch printf(foo.c_str()) and printf(foo->c_str())
2351
match = re.search(r'\b((?:string)?printf)\s*\(([\w.\->()]+)\)', line, re.I)
2353
error(filename, linenum, 'runtime/printf', 4,
2354
'Potential format string bug. Do %s("%%s", %s) instead.'
2355
% (match.group(1), match.group(2)))
2357
# Check for potential memset bugs like memset(buf, sizeof(buf), 0).
2358
match = Search(r'memset\s*\(([^,]*),\s*([^,]*),\s*0\s*\)', line)
2359
if match and not Match(r"^''|-?[0-9]+|0x[0-9A-Fa-f]$", match.group(2)):
2360
error(filename, linenum, 'runtime/memset', 4,
2361
'Did you mean "memset(%s, 0, %s)"?'
2362
% (match.group(1), match.group(2)))
2364
if Search(r'\busing namespace\b', line) and filename.endswith(".h"):
2365
error(filename, linenum, 'build/namespaces', 5,
2366
'Do not use namespace using-directives in headers. ')
2368
# Detect variable-length arrays.
2369
match = Match(r'\s*(.+::)?(\w+) [a-z]\w*\[(.+)];', line)
2370
if (match and match.group(2) != 'return' and match.group(2) != 'delete' and
2371
match.group(3).find(']') == -1):
2372
# Split the size using space and arithmetic operators as delimiters.
2373
# If any of the resulting tokens are not compile time constants then
2375
tokens = re.split(r'\s|\+|\-|\*|\/|<<|>>]', match.group(3))
2383
if Search(r'sizeof\(.+\)', tok): continue
2384
if Search(r'arraysize\(\w+\)', tok): continue
2386
tok = tok.lstrip('(')
2387
tok = tok.rstrip(')')
2388
if not tok: continue
2389
if Match(r'\d+', tok): continue
2390
if Match(r'0[xX][0-9a-fA-F]+', tok): continue
2391
if Match(r'k[A-Z0-9]\w*', tok): continue
2392
if Match(r'(.+::)?k[A-Z0-9]\w*', tok): continue
2393
if Match(r'(.+::)?[A-Z][A-Z0-9_]*', tok): continue
2394
# A catch all for tricky sizeof cases, including 'sizeof expression',
2395
# 'sizeof(*type)', 'sizeof(const type)', 'sizeof(struct StructName)'
2396
# requires skipping the next token becasue we split on ' ' and '*'.
2397
if tok.startswith('sizeof'):
2403
error(filename, linenum, 'runtime/arrays', 1,
2404
'Do not use variable-length arrays. Use an appropriately named '
2405
"('k' followed by CamelCase) compile-time constant for the size.")
2407
# If DISALLOW_EVIL_CONSTRUCTORS, DISALLOW_COPY_AND_ASSIGN, or
2408
# DISALLOW_IMPLICIT_CONSTRUCTORS is present, then it should be the last thing
2409
# in the class declaration.
2412
r'(DISALLOW_(EVIL_CONSTRUCTORS|COPY_AND_ASSIGN|IMPLICIT_CONSTRUCTORS))'
2415
if match and linenum + 1 < clean_lines.NumLines():
2416
next_line = clean_lines.elided[linenum + 1]
2417
if not Search(r'^\s*};', next_line):
2418
error(filename, linenum, 'readability/constructors', 3,
2419
match.group(1) + ' should be the last thing in the class')
2421
# Check for use of unnamed namespaces in header files. Registration
2422
# macros are typically OK, so we allow use of "namespace {" on lines
2423
# that end with backslashes.
2424
if (file_extension == 'h'
2425
and Search(r'\bnamespace\s*{', line)
2426
and line[-1] != '\\'):
2427
error(filename, linenum, 'build/namespaces', 4,
2428
'Do not use unnamed namespaces in header files. See '
2429
'http://google-styleguide.googlecode.com/svn/trunk/cppguide.xml#Namespaces'
2430
' for more information.')
2433
def CheckCStyleCast(filename, linenum, line, raw_line, cast_type, pattern,
2435
"""Checks for a C-style cast by looking for the pattern.
2437
This also handles sizeof(type) warnings, due to similarity of content.
2440
filename: The name of the current file.
2441
linenum: The number of the line to check.
2442
line: The line of code to check.
2443
raw_line: The raw line of code to check, with comments.
2444
cast_type: The string for the C++ cast to recommend. This is either
2445
reinterpret_cast or static_cast, depending.
2446
pattern: The regular expression used to find C-style casts.
2447
error: The function to call with any errors found.
2449
match = Search(pattern, line)
2454
sizeof_match = Match(r'.*sizeof\s*$', line[0:match.start(1) - 1])
2456
error(filename, linenum, 'runtime/sizeof', 1,
2457
'Using sizeof(type). Use sizeof(varname) instead if possible')
2460
remainder = line[match.end(0):]
2462
# The close paren is for function pointers as arguments to a function.
2463
# eg, void foo(void (*bar)(int));
2464
# The semicolon check is a more basic function check; also possibly a
2465
# function pointer typedef.
2466
# eg, void foo(int); or void foo(int) const;
2467
# The equals check is for function pointer assignment.
2468
# eg, void *(*foo)(int) = ...
2470
# Right now, this will only catch cases where there's a single argument, and
2471
# it's unnamed. It should probably be expanded to check for multiple
2472
# arguments with some unnamed.
2473
function_match = Match(r'\s*(\)|=|(const)?\s*(;|\{|throw\(\)))', remainder)
2475
if (not function_match.group(3) or
2476
function_match.group(3) == ';' or
2477
raw_line.find('/*') < 0):
2478
error(filename, linenum, 'readability/function', 3,
2479
'All parameters should be named in a function')
2482
# At this point, all that should be left is actual casts.
2483
error(filename, linenum, 'readability/casting', 4,
2484
'Using C-style cast. Use %s<%s>(...) instead' %
2485
(cast_type, match.group(1)))
2488
_HEADERS_CONTAINING_TEMPLATES = (
2489
('<deque>', ('deque',)),
2490
('<functional>', ('unary_function', 'binary_function',
2491
'plus', 'minus', 'multiplies', 'divides', 'modulus',
2493
'equal_to', 'not_equal_to', 'greater', 'less',
2494
'greater_equal', 'less_equal',
2495
'logical_and', 'logical_or', 'logical_not',
2496
'unary_negate', 'not1', 'binary_negate', 'not2',
2497
'bind1st', 'bind2nd',
2498
'pointer_to_unary_function',
2499
'pointer_to_binary_function',
2501
'mem_fun_t', 'mem_fun', 'mem_fun1_t', 'mem_fun1_ref_t',
2503
'const_mem_fun_t', 'const_mem_fun1_t',
2504
'const_mem_fun_ref_t', 'const_mem_fun1_ref_t',
2507
('<limits>', ('numeric_limits',)),
2508
('<list>', ('list',)),
2509
('<map>', ('map', 'multimap',)),
2510
('<memory>', ('allocator',)),
2511
('<queue>', ('queue', 'priority_queue',)),
2512
('<set>', ('set', 'multiset',)),
2513
('<stack>', ('stack',)),
2514
('<string>', ('char_traits', 'basic_string',)),
2515
('<utility>', ('pair',)),
2516
('<vector>', ('vector',)),
2519
# Note: std::hash is their hash, ::hash is our hash
2520
('<hash_map>', ('hash_map', 'hash_multimap',)),
2521
('<hash_set>', ('hash_set', 'hash_multiset',)),
2522
('<slist>', ('slist',)),
2525
_HEADERS_ACCEPTED_BUT_NOT_PROMOTED = {
2526
# We can trust with reasonable confidence that map gives us pair<>, too.
2527
'pair<>': ('map', 'multimap', 'hash_map', 'hash_multimap')
2530
_RE_PATTERN_STRING = re.compile(r'\bstring\b')
2532
_re_pattern_algorithm_header = []
2533
for _template in ('copy', 'max', 'min', 'min_element', 'sort', 'swap',
2535
# Match max<type>(..., ...), max(..., ...), but not foo->max, foo.max or
2537
_re_pattern_algorithm_header.append(
2538
(re.compile(r'[^>.]\b' + _template + r'(<.*?>)?\([^\)]'),
2542
_re_pattern_templates = []
2543
for _header, _templates in _HEADERS_CONTAINING_TEMPLATES:
2544
for _template in _templates:
2545
_re_pattern_templates.append(
2546
(re.compile(r'(\<|\b)' + _template + r'\s*\<'),
2551
def FilesBelongToSameModule(filename_cc, filename_h):
2552
"""Check if these two filenames belong to the same module.
2554
The concept of a 'module' here is a as follows:
2555
foo.h, foo-inl.h, foo.cc, foo_test.cc and foo_unittest.cc belong to the
2556
same 'module' if they are in the same directory.
2557
some/path/public/xyzzy and some/path/internal/xyzzy are also considered
2558
to belong to the same module here.
2560
If the filename_cc contains a longer path than the filename_h, for example,
2561
'/absolute/path/to/base/sysinfo.cc', and this file would include
2562
'base/sysinfo.h', this function also produces the prefix needed to open the
2563
header. This is used by the caller of this function to more robustly open the
2564
header file. We don't have access to the real include paths in this context,
2565
so we need this guesswork here.
2567
Known bugs: tools/base/bar.cc and base/bar.h belong to the same module
2568
according to this implementation. Because of this, this function gives
2569
some false positives. This should be sufficiently rare in practice.
2572
filename_cc: is the path for the .cc file
2573
filename_h: is the path for the header path
2576
Tuple with a bool and a string:
2577
bool: True if filename_cc and filename_h belong to the same module.
2578
string: the additional prefix needed to open the header file.
2581
if not filename_cc.endswith('.cc'):
2583
filename_cc = filename_cc[:-len('.cc')]
2584
if filename_cc.endswith('_unittest'):
2585
filename_cc = filename_cc[:-len('_unittest')]
2586
elif filename_cc.endswith('_test'):
2587
filename_cc = filename_cc[:-len('_test')]
2588
filename_cc = filename_cc.replace('/public/', '/')
2589
filename_cc = filename_cc.replace('/internal/', '/')
2591
if not filename_h.endswith('.h'):
2593
filename_h = filename_h[:-len('.h')]
2594
if filename_h.endswith('-inl'):
2595
filename_h = filename_h[:-len('-inl')]
2596
filename_h = filename_h.replace('/public/', '/')
2597
filename_h = filename_h.replace('/internal/', '/')
2599
files_belong_to_same_module = filename_cc.endswith(filename_h)
2601
if files_belong_to_same_module:
2602
common_path = filename_cc[:-len(filename_h)]
2603
return files_belong_to_same_module, common_path
2606
def UpdateIncludeState(filename, include_state, io=codecs):
2607
"""Fill up the include_state with new includes found from the file.
2610
filename: the name of the header to read.
2611
include_state: an _IncludeState instance in which the headers are inserted.
2612
io: The io factory to use to read the file. Provided for testability.
2615
True if a header was succesfully added. False otherwise.
2619
headerfile = io.open(filename, 'r', 'utf8', 'replace')
2622
_cpplint_state.seen_file(filename)
2624
for line in headerfile:
2626
clean_line = CleanseComments(line)
2627
match = _RE_PATTERN_INCLUDE.search(clean_line)
2629
include = match.group(2)
2630
# The value formatting is cute, but not really used right now.
2631
# What matters here is that the key is in include_state.
2632
include_state.setdefault(include, '%s:%d' % (filename, linenum))
2636
def CheckForIncludeWhatYouUse(filename, clean_lines, include_state, error,
2638
"""Reports for missing stl includes.
2640
This function will output warnings to make sure you are including the headers
2641
necessary for the stl containers and functions that you use. We only give one
2642
reason to include a header. For example, if you use both equal_to<> and
2643
less<> in a .h file, only one (the latter in the file) of these will be
2644
reported as a reason to include the <functional>.
2647
filename: The name of the current file.
2648
clean_lines: A CleansedLines instance containing the file.
2649
include_state: An _IncludeState instance.
2650
error: The function to call with any errors found.
2651
io: The IO factory to use to read the header file. Provided for unittest
2654
required = {} # A map of header name to linenumber and the template entity.
2655
# Example of required: { '<functional>': (1219, 'less<>') }
2657
for linenum in xrange(clean_lines.NumLines()):
2658
line = clean_lines.elided[linenum]
2659
if not line or line[0] == '#':
2662
# String is special -- it is a non-templatized type in STL.
2663
if _RE_PATTERN_STRING.search(line):
2664
required['<string>'] = (linenum, 'string')
2666
for pattern, template, header in _re_pattern_algorithm_header:
2667
if pattern.search(line):
2668
required[header] = (linenum, template)
2670
# The following function is just a speed up, no semantics are changed.
2671
if not '<' in line: # Reduces the cpu time usage by skipping lines.
2674
for pattern, template, header in _re_pattern_templates:
2675
if pattern.search(line):
2676
required[header] = (linenum, template)
2678
# The policy is that if you #include something in foo.h you don't need to
2679
# include it again in foo.cc. Here, we will look at possible includes.
2680
# Let's copy the include_state so it is only messed up within this function.
2681
include_state = include_state.copy()
2683
# Did we find the header for this file (if any) and succesfully load it?
2684
header_found = False
2686
# Use the absolute path so that matching works properly.
2687
abs_filename = os.path.abspath(filename)
2689
# For Emacs's flymake.
2690
# If cpplint is invoked from Emacs's flymake, a temporary file is generated
2691
# by flymake and that file name might end with '_flymake.cc'. In that case,
2692
# restore original file name here so that the corresponding header file can be
2694
# e.g. If the file name is 'foo_flymake.cc', we should search for 'foo.h'
2695
# instead of 'foo_flymake.h'
2696
emacs_flymake_suffix = '_flymake.cc'
2697
if abs_filename.endswith(emacs_flymake_suffix):
2698
abs_filename = abs_filename[:-len(emacs_flymake_suffix)] + '.cc'
2700
# include_state is modified during iteration, so we iterate over a copy of
2702
for header in include_state.keys(): #NOLINT
2703
(same_module, common_path) = FilesBelongToSameModule(abs_filename, header)
2704
fullpath = common_path + header
2705
if same_module and UpdateIncludeState(fullpath, include_state, io):
2708
# If we can't find the header file for a .cc, assume it's because we don't
2709
# know where to look. In that case we'll give up as we're not sure they
2710
# didn't include it in the .h file.
2711
# TODO(unknown): Do a better job of finding .h files so we are confident that
2712
# not having the .h file means there isn't one.
2713
if filename.endswith('.cc') and not header_found:
2716
# All the lines have been processed, report the errors found.
2717
for required_header_unstripped in required:
2718
template = required[required_header_unstripped][1]
2719
if template in _HEADERS_ACCEPTED_BUT_NOT_PROMOTED:
2720
headers = _HEADERS_ACCEPTED_BUT_NOT_PROMOTED[template]
2721
if [True for header in headers if header in include_state]:
2723
if required_header_unstripped.strip('<>"') not in include_state:
2724
error(filename, required[required_header_unstripped][0],
2725
'build/include_what_you_use', 4,
2726
'Add #include ' + required_header_unstripped + ' for ' + template)
2729
def ProcessLine(filename, file_extension,
2730
clean_lines, line, include_state, function_state,
2731
class_state, error):
2732
"""Processes a single line in the file.
2735
filename: Filename of the file that is being processed.
2736
file_extension: The extension (dot not included) of the file.
2737
clean_lines: An array of strings, each representing a line of the file,
2738
with comments stripped.
2739
line: Number of line being processed.
2740
include_state: An _IncludeState instance in which the headers are inserted.
2741
function_state: A _FunctionState instance which counts function lines, etc.
2742
class_state: A _ClassState instance which maintains information about
2743
the current stack of nested class declarations being parsed.
2744
error: A callable to which errors are reported, which takes 4 arguments:
2745
filename, line number, error level, and message
2748
raw_lines = clean_lines.raw_lines
2749
CheckForFunctionLengths(filename, clean_lines, line, function_state, error)
2750
if Search(r'\bNOLINT\b', raw_lines[line]): # ignore nolint lines
2752
CheckForMultilineCommentsAndStrings(filename, clean_lines, line, error)
2753
CheckStyle(filename, clean_lines, line, file_extension, error)
2754
CheckLanguage(filename, clean_lines, line, file_extension, include_state,
2756
CheckForNonStandardConstructs(filename, clean_lines, line,
2758
CheckPosixThreading(filename, clean_lines, line, error)
2759
CheckInvalidIncrement(filename, clean_lines, line, error)
2762
def ProcessFileData(filename, file_extension, lines, error):
2763
"""Performs lint checks and reports any errors to the given error function.
2766
filename: Filename of the file that is being processed.
2767
file_extension: The extension (dot not included) of the file.
2768
lines: An array of strings, each representing a line of the file, with the
2769
last element being empty if the file is termined with a newline.
2770
error: A callable to which errors are reported, which takes 4 arguments:
2772
lines = (['// marker so line numbers and indices both start at 1'] + lines +
2773
['// marker so line numbers end in a known way'])
2775
include_state = _IncludeState()
2776
function_state = _FunctionState()
2777
class_state = _ClassState()
2779
CheckForCopyright(filename, lines, error)
2781
if file_extension == 'h':
2782
CheckForHeaderGuard(filename, lines, error)
2784
RemoveMultiLineComments(filename, lines, error)
2785
clean_lines = CleansedLines(lines)
2786
for line in xrange(clean_lines.NumLines()):
2787
ProcessLine(filename, file_extension, clean_lines, line,
2788
include_state, function_state, class_state, error)
2789
class_state.CheckFinished(filename, error)
2791
CheckForIncludeWhatYouUse(filename, clean_lines, include_state, error)
2793
# We check here rather than inside ProcessLine so that we see raw
2794
# lines rather than "cleaned" lines.
2795
CheckForUnicodeReplacementCharacters(filename, lines, error)
2797
CheckForNewlineAtEOF(filename, lines, error)
2800
def ProcessFile(filename, vlevel):
2801
"""Does google-lint on a single file.
2804
filename: The name of the file to parse.
2806
vlevel: The level of errors to report. Every error of confidence
2807
>= verbose_level will be reported. 0 is a good default.
2810
_SetVerboseLevel(vlevel)
2813
# Support the UNIX convention of using "-" for stdin. Note that
2814
# we are not opening the file with universal newline support
2815
# (which codecs doesn't support anyway), so the resulting lines do
2816
# contain trailing '\r' characters if we are reading a file that
2818
# If after the split a trailing '\r' is present, it is removed
2819
# below. If it is not expected to be present (i.e. os.linesep !=
2820
# '\r\n' as in Windows), a warning is issued below if this file
2824
lines = codecs.StreamReaderWriter(sys.stdin,
2825
codecs.getreader('utf8'),
2826
codecs.getwriter('utf8'),
2827
'replace').read().split('\n')
2829
_cpplint_state.seen_file(filename)
2830
lines = codecs.open(filename, 'r', 'utf8', 'replace').read().split('\n')
2832
carriage_return_found = False
2833
# Remove trailing '\r'.
2834
for linenum in range(len(lines)):
2835
if lines[linenum].endswith('\r'):
2836
lines[linenum] = lines[linenum].rstrip('\r')
2837
carriage_return_found = True
2841
"Skipping input '%s': Can't open for reading\n" % filename)
2844
# Note, if no dot is found, this will give the entire filename as the ext.
2845
file_extension = filename[filename.rfind('.') + 1:]
2847
# When reading from stdin, the extension is unknown, so no cpplint tests
2848
# should rely on the extension.
2849
if (filename != '-' and file_extension != 'cc' and file_extension != 'h'
2850
and file_extension != 'cpp'):
2851
sys.stderr.write('Ignoring %s; not a .cc or .h file\n' % filename)
2853
ProcessFileData(filename, file_extension, lines, Error)
2854
if carriage_return_found and os.linesep != '\r\n':
2855
# Use 0 for linenum since outputing only one error for potentially
2857
Error(filename, 0, 'whitespace/newline', 1,
2858
'One or more unexpected \\r (^M) found;'
2859
'better to use only a \\n')
2861
sys.stderr.write('Done processing %s\n' % filename)
2864
def PrintUsage(message):
2865
"""Prints a brief usage string and exits, optionally with an error message.
2868
message: The optional error message.
2870
sys.stderr.write(_USAGE)
2872
sys.exit('\nFATAL ERROR: ' + message)
2877
def PrintCategories():
2878
"""Prints a list of all the error-categories used by error messages.
2880
These are the categories used to filter messages via --filter.
2882
sys.stderr.write(_ERROR_CATEGORIES)
2886
def ParseArguments(args):
2887
"""Parses the command line arguments.
2889
This may set the output format and verbosity level as side-effects.
2892
args: The command line arguments:
2895
The list of filenames to lint.
2898
(opts, filenames) = getopt.getopt(args, '',
2899
['help', 'output=', 'verbose=', 'deps=', 'filter='])
2900
except getopt.GetoptError:
2901
PrintUsage('Invalid arguments.')
2903
verbosity = _VerboseLevel()
2904
output_format = _OutputFormat()
2907
for (opt, val) in opts:
2910
elif opt == '--output':
2911
if not val in ('emacs', 'vs7'):
2912
PrintUsage('The only allowed output formats are emacs and vs7.')
2914
elif opt == '--verbose':
2915
verbosity = int(val)
2916
elif opt == '--filter':
2920
elif opt == '--deps':
2921
_cpplint_state.depfilename = val
2924
PrintUsage('No files were specified.')
2926
_SetOutputFormat(output_format)
2927
_SetVerboseLevel(verbosity)
2928
_SetFilters(filters)
2934
filenames = ParseArguments(sys.argv[1:])
2936
# Change stderr to write with replacement characters so we don't die
2937
# if we try to print something containing non-ASCII characters.
2938
sys.stderr = codecs.StreamReaderWriter(sys.stderr,
2939
codecs.getreader('utf8'),
2940
codecs.getwriter('utf8'),
2943
_cpplint_state.ResetErrorCount()
2944
for filename in filenames:
2945
ProcessFile(filename, _cpplint_state.verbose_level)
2946
_cpplint_state.finished()
2947
sys.stderr.write('Total errors found: %d\n' % _cpplint_state.error_count)
2948
sys.exit(_cpplint_state.error_count > 0)
2951
if __name__ == '__main__':