80a98681510f739d4418035144be553d7daa5344
[WebKit-https.git] / WebKitTools / Scripts / modules / cpp_style_unittest.py
1 #!/usr/bin/python
2 # -*- coding: utf-8; -*-
3 #
4 # Copyright (C) 2009 Google Inc. All rights reserved.
5 # Copyright (C) 2009 Torch Mobile Inc.
6 # Copyright (C) 2009 Apple Inc. All rights reserved.
7 #
8 # Redistribution and use in source and binary forms, with or without
9 # modification, are permitted provided that the following conditions are
10 # met:
11 #
12 #    * Redistributions of source code must retain the above copyright
13 # notice, this list of conditions and the following disclaimer.
14 #    * Redistributions in binary form must reproduce the above
15 # copyright notice, this list of conditions and the following disclaimer
16 # in the documentation and/or other materials provided with the
17 # distribution.
18 #    * Neither the name of Google Inc. nor the names of its
19 # contributors may be used to endorse or promote products derived from
20 # this software without specific prior written permission.
21 #
22 # THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
23 # "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
24 # LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
25 # A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
26 # OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
27 # SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
28 # LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
29 # DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
30 # THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
31 # (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
32 # OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33
34 """Unit test for cpp_style.py."""
35
36 # FIXME: Add a good test that tests UpdateIncludeState.
37
38 import codecs
39 import os
40 import random
41 import re
42 import unittest
43 import cpp_style
44
45
46 # This class works as an error collector and replaces cpp_style.Error
47 # function for the unit tests.  We also verify each category we see
48 # is in cpp_style._STYLE_CATEGORIES, to help keep that list up to date.
49 class ErrorCollector:
50     _all_style_categories = cpp_style._STYLE_CATEGORIES
51     # This a list including all categories seen in any unit test.
52     _seen_style_categories = {}
53
54     def __init__(self, assert_fn):
55         """assert_fn: a function to call when we notice a problem."""
56         self._assert_fn = assert_fn
57         self._errors = []
58
59     def __call__(self, unused_filename, unused_linenum,
60                  category, confidence, message):
61         self._assert_fn(category in self._all_style_categories,
62                         'Message "%s" has category "%s",'
63                         ' which is not in _STYLE_CATEGORIES' % (message, category))
64         self._seen_style_categories[category] = 1
65         if cpp_style._should_print_error(category, confidence):
66             self._errors.append('%s  [%s] [%d]' % (message, category, confidence))
67
68     def results(self):
69         if len(self._errors) < 2:
70             return ''.join(self._errors)  # Most tests expect to have a string.
71         else:
72             return self._errors  # Let's give a list if there is more than one.
73
74     def result_list(self):
75         return self._errors
76
77     def verify_all_categories_are_seen(self):
78         """Fails if there's a category in _all_style_categories - _seen_style_categories.
79
80         This should only be called after all tests are run, so
81         _seen_style_categories has had a chance to fully populate.  Since
82         this isn't called from within the normal unittest framework, we
83         can't use the normal unittest assert macros.  Instead we just exit
84         when we see an error.  Good thing this test is always run last!
85         """
86         for category in self._all_style_categories:
87             if category not in self._seen_style_categories:
88                 import sys
89                 sys.exit('FATAL ERROR: There are no tests for category "%s"' % category)
90
91     def remove_if_present(self, substr):
92         for (index, error) in enumerate(self._errors):
93             if error.find(substr) != -1:
94                 self._errors = self._errors[0:index] + self._errors[(index + 1):]
95                 break
96
97
98 # This class is a lame mock of codecs. We do not verify filename, mode, or
99 # encoding, but for the current use case it is not needed.
100 class MockIo:
101     def __init__(self, mock_file):
102         self.mock_file = mock_file
103
104     def open(self, unused_filename, unused_mode, unused_encoding, _):  # NOLINT
105         # (lint doesn't like open as a method name)
106         return self.mock_file
107
108
109 class CppStyleTestBase(unittest.TestCase):
110     """Provides some useful helper functions for cpp_style tests."""
111
112     # Perform lint on single line of input and return the error message.
113     def perform_single_line_lint(self, code, file_name):
114         error_collector = ErrorCollector(self.assert_)
115         lines = code.split('\n')
116         cpp_style.remove_multi_line_comments(file_name, lines, error_collector)
117         clean_lines = cpp_style.CleansedLines(lines)
118         include_state = cpp_style._IncludeState()
119         function_state = cpp_style._FunctionState()
120         ext = file_name[file_name.rfind('.') + 1:]
121         class_state = cpp_style._ClassState()
122         file_state = cpp_style._FileState()
123         cpp_style.process_line(file_name, ext, clean_lines, 0,
124                                include_state, function_state,
125                                class_state, file_state, error_collector)
126         # Single-line lint tests are allowed to fail the 'unlintable function'
127         # check.
128         error_collector.remove_if_present(
129             'Lint failed to find start of function body.')
130         return error_collector.results()
131
132     # Perform lint over multiple lines and return the error message.
133     def perform_multi_line_lint(self, code, file_name):
134         error_collector = ErrorCollector(self.assert_)
135         lines = code.split('\n')
136         cpp_style.remove_multi_line_comments(file_name, lines, error_collector)
137         lines = cpp_style.CleansedLines(lines)
138         ext = file_name[file_name.rfind('.') + 1:]
139         class_state = cpp_style._ClassState()
140         file_state = cpp_style._FileState()
141         for i in xrange(lines.num_lines()):
142             cpp_style.check_style(file_name, lines, i, ext, file_state, error_collector)
143             cpp_style.check_for_non_standard_constructs(file_name, lines, i, class_state,
144                                                         error_collector)
145         class_state.check_finished(file_name, error_collector)
146         return error_collector.results()
147
148     # Similar to perform_multi_line_lint, but calls check_language instead of
149     # check_for_non_standard_constructs
150     def perform_language_rules_check(self, file_name, code):
151         error_collector = ErrorCollector(self.assert_)
152         include_state = cpp_style._IncludeState()
153         lines = code.split('\n')
154         cpp_style.remove_multi_line_comments(file_name, lines, error_collector)
155         lines = cpp_style.CleansedLines(lines)
156         ext = file_name[file_name.rfind('.') + 1:]
157         for i in xrange(lines.num_lines()):
158             cpp_style.check_language(file_name, lines, i, ext, include_state,
159                                      error_collector)
160         return error_collector.results()
161
162     def perform_function_lengths_check(self, code):
163         """Perform Lint function length check on block of code and return warnings.
164
165         Builds up an array of lines corresponding to the code and strips comments
166         using cpp_style functions.
167
168         Establishes an error collector and invokes the function length checking
169         function following cpp_style's pattern.
170
171         Args:
172           code: C++ source code expected to generate a warning message.
173
174         Returns:
175           The accumulated errors.
176         """
177         file_name = 'foo.cpp'
178         error_collector = ErrorCollector(self.assert_)
179         function_state = cpp_style._FunctionState()
180         lines = code.split('\n')
181         cpp_style.remove_multi_line_comments(file_name, lines, error_collector)
182         lines = cpp_style.CleansedLines(lines)
183         for i in xrange(lines.num_lines()):
184             cpp_style.check_for_function_lengths(file_name, lines, i,
185                                                  function_state, error_collector)
186         return error_collector.results()
187
188     def perform_include_what_you_use(self, code, filename='foo.h', io=codecs):
189         # First, build up the include state.
190         error_collector = ErrorCollector(self.assert_)
191         include_state = cpp_style._IncludeState()
192         lines = code.split('\n')
193         cpp_style.remove_multi_line_comments(filename, lines, error_collector)
194         lines = cpp_style.CleansedLines(lines)
195         for i in xrange(lines.num_lines()):
196             cpp_style.check_language(filename, lines, i, '.h', include_state,
197                                      error_collector)
198         # We could clear the error_collector here, but this should
199         # also be fine, since our IncludeWhatYouUse unittests do not
200         # have language problems.
201
202         # Second, look for missing includes.
203         cpp_style.check_for_include_what_you_use(filename, lines, include_state,
204                                                  error_collector, io)
205         return error_collector.results()
206
207     # Perform lint and compare the error message with "expected_message".
208     def assert_lint(self, code, expected_message, file_name='foo.cpp'):
209         self.assertEquals(expected_message, self.perform_single_line_lint(code, file_name))
210
211     def assert_lint_one_of_many_errors_re(self, code, expected_message_re, file_name='foo.cpp'):
212         messages = self.perform_single_line_lint(code, file_name)
213         for message in messages:
214             if re.search(expected_message_re, message):
215                 return
216
217         self.assertEquals(expected_message, messages)
218
219     def assert_multi_line_lint(self, code, expected_message, file_name='foo.h'):
220         self.assertEquals(expected_message, self.perform_multi_line_lint(code, file_name))
221
222     def assert_multi_line_lint_re(self, code, expected_message_re, file_name='foo.h'):
223         message = self.perform_multi_line_lint(code, file_name)
224         if not re.search(expected_message_re, message):
225             self.fail('Message was:\n' + message + 'Expected match to "' + expected_message_re + '"')
226
227     def assert_language_rules_check(self, file_name, code, expected_message):
228         self.assertEquals(expected_message,
229                           self.perform_language_rules_check(file_name, code))
230
231     def assert_include_what_you_use(self, code, expected_message):
232         self.assertEquals(expected_message,
233                           self.perform_include_what_you_use(code))
234
235     def assert_blank_lines_check(self, lines, start_errors, end_errors):
236         error_collector = ErrorCollector(self.assert_)
237         cpp_style.process_file_data('foo.cpp', 'cpp', lines, error_collector)
238         self.assertEquals(
239             start_errors,
240             error_collector.results().count(
241                 'Blank line at the start of a code block.  Is this needed?'
242                 '  [whitespace/blank_line] [2]'))
243         self.assertEquals(
244             end_errors,
245             error_collector.results().count(
246                 'Blank line at the end of a code block.  Is this needed?'
247                 '  [whitespace/blank_line] [3]'))
248
249
250 class CppStyleTest(CppStyleTestBase):
251
252     # Test get line width.
253     def test_get_line_width(self):
254         self.assertEquals(0, cpp_style.get_line_width(''))
255         self.assertEquals(10, cpp_style.get_line_width(u'x' * 10))
256         self.assertEquals(16, cpp_style.get_line_width(u'都|道|府|県|支庁'))
257
258     def test_find_next_multi_line_comment_start(self):
259         self.assertEquals(1, cpp_style.find_next_multi_line_comment_start([''], 0))
260
261         lines = ['a', 'b', '/* c']
262         self.assertEquals(2, cpp_style.find_next_multi_line_comment_start(lines, 0))
263
264         lines = ['char a[] = "/*";']  # not recognized as comment.
265         self.assertEquals(1, cpp_style.find_next_multi_line_comment_start(lines, 0))
266
267     def test_find_next_multi_line_comment_end(self):
268         self.assertEquals(1, cpp_style.find_next_multi_line_comment_end([''], 0))
269         lines = ['a', 'b', ' c */']
270         self.assertEquals(2, cpp_style.find_next_multi_line_comment_end(lines, 0))
271
272     def test_remove_multi_line_comments_from_range(self):
273         lines = ['a', '  /* comment ', ' * still comment', ' comment */   ', 'b']
274         cpp_style.remove_multi_line_comments_from_range(lines, 1, 4)
275         self.assertEquals(['a', '// dummy', '// dummy', '// dummy', 'b'], lines)
276
277     def test_spaces_at_end_of_line(self):
278         self.assert_lint(
279             '// Hello there ',
280             'Line ends in whitespace.  Consider deleting these extra spaces.'
281             '  [whitespace/end_of_line] [4]')
282
283     # Test C-style cast cases.
284     def test_cstyle_cast(self):
285         self.assert_lint(
286             'int a = (int)1.0;',
287             'Using C-style cast.  Use static_cast<int>(...) instead'
288             '  [readability/casting] [4]')
289         self.assert_lint(
290             'int *a = (int *)DEFINED_VALUE;',
291             'Using C-style cast.  Use reinterpret_cast<int *>(...) instead'
292             '  [readability/casting] [4]', 'foo.c')
293         self.assert_lint(
294             'uint16 a = (uint16)1.0;',
295             'Using C-style cast.  Use static_cast<uint16>(...) instead'
296             '  [readability/casting] [4]')
297         self.assert_lint(
298             'int32 a = (int32)1.0;',
299             'Using C-style cast.  Use static_cast<int32>(...) instead'
300             '  [readability/casting] [4]')
301         self.assert_lint(
302             'uint64 a = (uint64)1.0;',
303             'Using C-style cast.  Use static_cast<uint64>(...) instead'
304             '  [readability/casting] [4]')
305
306     # Test taking address of casts (runtime/casting)
307     def test_runtime_casting(self):
308         self.assert_lint(
309             'int* x = &static_cast<int*>(foo);',
310             'Are you taking an address of a cast?  '
311             'This is dangerous: could be a temp var.  '
312             'Take the address before doing the cast, rather than after'
313             '  [runtime/casting] [4]')
314
315         self.assert_lint(
316             'int* x = &dynamic_cast<int *>(foo);',
317             ['Are you taking an address of a cast?  '
318              'This is dangerous: could be a temp var.  '
319              'Take the address before doing the cast, rather than after'
320              '  [runtime/casting] [4]',
321              'Do not use dynamic_cast<>.  If you need to cast within a class '
322              'hierarchy, use static_cast<> to upcast.  Google doesn\'t support '
323              'RTTI.  [runtime/rtti] [5]'])
324
325         self.assert_lint(
326             'int* x = &reinterpret_cast<int *>(foo);',
327             'Are you taking an address of a cast?  '
328             'This is dangerous: could be a temp var.  '
329             'Take the address before doing the cast, rather than after'
330             '  [runtime/casting] [4]')
331
332         # It's OK to cast an address.
333         self.assert_lint(
334             'int* x = reinterpret_cast<int *>(&foo);',
335             '')
336
337     def test_runtime_selfinit(self):
338         self.assert_lint(
339             'Foo::Foo(Bar r, Bel l) : r_(r_), l_(l_) { }',
340             'You seem to be initializing a member variable with itself.'
341             '  [runtime/init] [4]')
342         self.assert_lint(
343             'Foo::Foo(Bar r, Bel l) : r_(r), l_(l) { }',
344             '')
345         self.assert_lint(
346             'Foo::Foo(Bar r) : r_(r), l_(r_), ll_(l_) { }',
347             '')
348
349     def test_runtime_rtti(self):
350         statement = 'int* x = dynamic_cast<int*>(&foo);'
351         error_message = (
352             'Do not use dynamic_cast<>.  If you need to cast within a class '
353             'hierarchy, use static_cast<> to upcast.  Google doesn\'t support '
354             'RTTI.  [runtime/rtti] [5]')
355         # dynamic_cast is disallowed in most files.
356         self.assert_language_rules_check('foo.cpp', statement, error_message)
357         self.assert_language_rules_check('foo.h', statement, error_message)
358         # It is explicitly allowed in tests, however.
359         self.assert_language_rules_check('foo_test.cpp', statement, '')
360         self.assert_language_rules_check('foo_unittest.cpp', statement, '')
361         self.assert_language_rules_check('foo_regtest.cpp', statement, '')
362
363     # We cannot test this functionality because of difference of
364     # function definitions.  Anyway, we may never enable this.
365     #
366     # # Test for unnamed arguments in a method.
367     # def test_check_for_unnamed_params(self):
368     #   message = ('All parameters should be named in a function'
369     #              '  [readability/function] [3]')
370     #   self.assert_lint('virtual void A(int*) const;', message)
371     #   self.assert_lint('virtual void B(void (*fn)(int*));', message)
372     #   self.assert_lint('virtual void C(int*);', message)
373     #   self.assert_lint('void *(*f)(void *) = x;', message)
374     #   self.assert_lint('void Method(char*) {', message)
375     #   self.assert_lint('void Method(char*);', message)
376     #   self.assert_lint('void Method(char* /*x*/);', message)
377     #   self.assert_lint('typedef void (*Method)(int32);', message)
378     #   self.assert_lint('static void operator delete[](void*) throw();', message)
379     # 
380     #   self.assert_lint('virtual void D(int* p);', '')
381     #   self.assert_lint('void operator delete(void* x) throw();', '')
382     #   self.assert_lint('void Method(char* x)\n{', '')
383     #   self.assert_lint('void Method(char* /*x*/)\n{', '')
384     #   self.assert_lint('void Method(char* x);', '')
385     #   self.assert_lint('typedef void (*Method)(int32 x);', '')
386     #   self.assert_lint('static void operator delete[](void* x) throw();', '')
387     #   self.assert_lint('static void operator delete[](void* /*x*/) throw();', '')
388     # 
389     #   # This one should technically warn, but doesn't because the function
390     #   # pointer is confusing.
391     #   self.assert_lint('virtual void E(void (*fn)(int* p));', '')
392
393     # Test deprecated casts such as int(d)
394     def test_deprecated_cast(self):
395         self.assert_lint(
396             'int a = int(2.2);',
397             'Using deprecated casting style.  '
398             'Use static_cast<int>(...) instead'
399             '  [readability/casting] [4]')
400         # Checks for false positives...
401         self.assert_lint(
402             'int a = int();  // Constructor, o.k.',
403             '')
404         self.assert_lint(
405             'X::X() : a(int()) {}  // default Constructor, o.k.',
406             '')
407         self.assert_lint(
408             'operator bool();  // Conversion operator, o.k.',
409             '')
410
411     # The second parameter to a gMock method definition is a function signature
412     # that often looks like a bad cast but should not picked up by lint.
413     def test_mock_method(self):
414         self.assert_lint(
415             'MOCK_METHOD0(method, int());',
416             '')
417         self.assert_lint(
418             'MOCK_CONST_METHOD1(method, float(string));',
419             '')
420         self.assert_lint(
421             'MOCK_CONST_METHOD2_T(method, double(float, float));',
422             '')
423
424     # Test sizeof(type) cases.
425     def test_sizeof_type(self):
426         self.assert_lint(
427             'sizeof(int);',
428             'Using sizeof(type).  Use sizeof(varname) instead if possible'
429             '  [runtime/sizeof] [1]')
430         self.assert_lint(
431             'sizeof(int *);',
432             'Using sizeof(type).  Use sizeof(varname) instead if possible'
433             '  [runtime/sizeof] [1]')
434
435     # Test typedef cases.  There was a bug that cpp_style misidentified
436     # typedef for pointer to function as C-style cast and produced
437     # false-positive error messages.
438     def test_typedef_for_pointer_to_function(self):
439         self.assert_lint(
440             'typedef void (*Func)(int x);',
441             '')
442         self.assert_lint(
443             'typedef void (*Func)(int *x);',
444             '')
445         self.assert_lint(
446             'typedef void Func(int x);',
447             '')
448         self.assert_lint(
449             'typedef void Func(int *x);',
450             '')
451
452     def test_include_what_you_use_no_implementation_files(self):
453         code = 'std::vector<int> foo;'
454         self.assertEquals('Add #include <vector> for vector<>'
455                           '  [build/include_what_you_use] [4]',
456                           self.perform_include_what_you_use(code, 'foo.h'))
457         self.assertEquals('',
458                           self.perform_include_what_you_use(code, 'foo.cpp'))
459
460     def test_include_what_you_use(self):
461         self.assert_include_what_you_use(
462             '''#include <vector>
463                std::vector<int> foo;
464             ''',
465             '')
466         self.assert_include_what_you_use(
467             '''#include <map>
468                std::pair<int,int> foo;
469             ''',
470             '')
471         self.assert_include_what_you_use(
472             '''#include <multimap>
473                std::pair<int,int> foo;
474             ''',
475             '')
476         self.assert_include_what_you_use(
477             '''#include <hash_map>
478                std::pair<int,int> foo;
479             ''',
480             '')
481         self.assert_include_what_you_use(
482             '''#include <utility>
483                std::pair<int,int> foo;
484             ''',
485             '')
486         self.assert_include_what_you_use(
487             '''#include <vector>
488                DECLARE_string(foobar);
489             ''',
490             '')
491         self.assert_include_what_you_use(
492             '''#include <vector>
493                DEFINE_string(foobar, "", "");
494             ''',
495             '')
496         self.assert_include_what_you_use(
497             '''#include <vector>
498                std::pair<int,int> foo;
499             ''',
500             'Add #include <utility> for pair<>'
501             '  [build/include_what_you_use] [4]')
502         self.assert_include_what_you_use(
503             '''#include "base/foobar.h"
504                std::vector<int> foo;
505             ''',
506             'Add #include <vector> for vector<>'
507             '  [build/include_what_you_use] [4]')
508         self.assert_include_what_you_use(
509             '''#include <vector>
510                std::set<int> foo;
511             ''',
512             'Add #include <set> for set<>'
513             '  [build/include_what_you_use] [4]')
514         self.assert_include_what_you_use(
515             '''#include "base/foobar.h"
516               hash_map<int, int> foobar;
517             ''',
518             'Add #include <hash_map> for hash_map<>'
519             '  [build/include_what_you_use] [4]')
520         self.assert_include_what_you_use(
521             '''#include "base/foobar.h"
522                bool foobar = std::less<int>(0,1);
523             ''',
524             'Add #include <functional> for less<>'
525             '  [build/include_what_you_use] [4]')
526         self.assert_include_what_you_use(
527             '''#include "base/foobar.h"
528                bool foobar = min<int>(0,1);
529             ''',
530             'Add #include <algorithm> for min  [build/include_what_you_use] [4]')
531         self.assert_include_what_you_use(
532             'void a(const string &foobar);',
533             'Add #include <string> for string  [build/include_what_you_use] [4]')
534         self.assert_include_what_you_use(
535             '''#include "base/foobar.h"
536                bool foobar = swap(0,1);
537             ''',
538             'Add #include <algorithm> for swap  [build/include_what_you_use] [4]')
539         self.assert_include_what_you_use(
540             '''#include "base/foobar.h"
541                bool foobar = transform(a.begin(), a.end(), b.start(), Foo);
542             ''',
543             'Add #include <algorithm> for transform  '
544             '[build/include_what_you_use] [4]')
545         self.assert_include_what_you_use(
546             '''#include "base/foobar.h"
547                bool foobar = min_element(a.begin(), a.end());
548             ''',
549             'Add #include <algorithm> for min_element  '
550             '[build/include_what_you_use] [4]')
551         self.assert_include_what_you_use(
552             '''foo->swap(0,1);
553                foo.swap(0,1);
554             ''',
555             '')
556         self.assert_include_what_you_use(
557             '''#include <string>
558                void a(const std::multimap<int,string> &foobar);
559             ''',
560             'Add #include <map> for multimap<>'
561             '  [build/include_what_you_use] [4]')
562         self.assert_include_what_you_use(
563             '''#include <queue>
564                void a(const std::priority_queue<int> &foobar);
565             ''',
566             '')
567         self.assert_include_what_you_use(
568              '''#include "base/basictypes.h"
569                 #include "base/port.h"
570                 #include <assert.h>
571                 #include <string>
572                 #include <vector>
573                 vector<string> hajoa;''', '')
574         self.assert_include_what_you_use(
575             '''#include <string>
576                int i = numeric_limits<int>::max()
577             ''',
578             'Add #include <limits> for numeric_limits<>'
579             '  [build/include_what_you_use] [4]')
580         self.assert_include_what_you_use(
581             '''#include <limits>
582                int i = numeric_limits<int>::max()
583             ''',
584             '')
585
586         # Test the UpdateIncludeState code path.
587         mock_header_contents = ['#include "blah/foo.h"', '#include "blah/bar.h"']
588         message = self.perform_include_what_you_use(
589             '#include "config.h"\n'
590             '#include "blah/a.h"\n',
591             filename='blah/a.cpp',
592             io=MockIo(mock_header_contents))
593         self.assertEquals(message, '')
594
595         mock_header_contents = ['#include <set>']
596         message = self.perform_include_what_you_use(
597             '''#include "config.h"
598                #include "blah/a.h"
599
600                std::set<int> foo;''',
601             filename='blah/a.cpp',
602             io=MockIo(mock_header_contents))
603         self.assertEquals(message, '')
604
605         # If there's just a .cpp and the header can't be found then it's ok.
606         message = self.perform_include_what_you_use(
607             '''#include "config.h"
608                #include "blah/a.h"
609
610                std::set<int> foo;''',
611             filename='blah/a.cpp')
612         self.assertEquals(message, '')
613
614         # Make sure we find the headers with relative paths.
615         mock_header_contents = ['']
616         message = self.perform_include_what_you_use(
617             '''#include "config.h"
618                #include "%s/a.h"
619
620                std::set<int> foo;''' % os.path.basename(os.getcwd()),
621             filename='a.cpp',
622             io=MockIo(mock_header_contents))
623         self.assertEquals(message, 'Add #include <set> for set<>  '
624                                    '[build/include_what_you_use] [4]')
625
626     def test_files_belong_to_same_module(self):
627         f = cpp_style.files_belong_to_same_module
628         self.assertEquals((True, ''), f('a.cpp', 'a.h'))
629         self.assertEquals((True, ''), f('base/google.cpp', 'base/google.h'))
630         self.assertEquals((True, ''), f('base/google_test.cpp', 'base/google.h'))
631         self.assertEquals((True, ''),
632                           f('base/google_unittest.cpp', 'base/google.h'))
633         self.assertEquals((True, ''),
634                           f('base/internal/google_unittest.cpp',
635                             'base/public/google.h'))
636         self.assertEquals((True, 'xxx/yyy/'),
637                           f('xxx/yyy/base/internal/google_unittest.cpp',
638                             'base/public/google.h'))
639         self.assertEquals((True, 'xxx/yyy/'),
640                           f('xxx/yyy/base/google_unittest.cpp',
641                             'base/public/google.h'))
642         self.assertEquals((True, ''),
643                           f('base/google_unittest.cpp', 'base/google-inl.h'))
644         self.assertEquals((True, '/home/build/google3/'),
645                           f('/home/build/google3/base/google.cpp', 'base/google.h'))
646
647         self.assertEquals((False, ''),
648                           f('/home/build/google3/base/google.cpp', 'basu/google.h'))
649         self.assertEquals((False, ''), f('a.cpp', 'b.h'))
650
651     def test_cleanse_line(self):
652         self.assertEquals('int foo = 0;  ',
653                           cpp_style.cleanse_comments('int foo = 0;  // danger!'))
654         self.assertEquals('int o = 0;',
655                           cpp_style.cleanse_comments('int /* foo */ o = 0;'))
656         self.assertEquals('foo(int a, int b);',
657                           cpp_style.cleanse_comments('foo(int a /* abc */, int b);'))
658         self.assertEqual('f(a, b);',
659                          cpp_style.cleanse_comments('f(a, /* name */ b);'))
660         self.assertEqual('f(a, b);',
661                          cpp_style.cleanse_comments('f(a /* name */, b);'))
662         self.assertEqual('f(a, b);',
663                          cpp_style.cleanse_comments('f(a, /* name */b);'))
664
665     def test_multi_line_comments(self):
666         # missing explicit is bad
667         self.assert_multi_line_lint(
668             r'''int a = 0;
669                 /* multi-liner
670                 class Foo {
671                 Foo(int f);  // should cause a lint warning in code
672                 }
673             */ ''',
674         '')
675         self.assert_multi_line_lint(
676             r'''/* int a = 0; multi-liner
677             static const int b = 0;''',
678       'Could not find end of multi-line comment'
679       '  [readability/multiline_comment] [5]')
680         self.assert_multi_line_lint(r'''    /* multi-line comment''',
681                                     'Could not find end of multi-line comment'
682                                     '  [readability/multiline_comment] [5]')
683         self.assert_multi_line_lint(r'''    // /* comment, but not multi-line''', '')
684
685     def test_multiline_strings(self):
686         multiline_string_error_message = (
687             'Multi-line string ("...") found.  This lint script doesn\'t '
688             'do well with such strings, and may give bogus warnings.  They\'re '
689             'ugly and unnecessary, and you should use concatenation instead".'
690             '  [readability/multiline_string] [5]')
691
692         file_path = 'mydir/foo.cpp'
693
694         error_collector = ErrorCollector(self.assert_)
695         cpp_style.process_file_data(file_path, 'cpp',
696                                     ['const char* str = "This is a\\',
697                                      ' multiline string.";'],
698                                     error_collector)
699         self.assertEquals(
700             2,  # One per line.
701             error_collector.result_list().count(multiline_string_error_message))
702
703     # Test non-explicit single-argument constructors
704     def test_explicit_single_argument_constructors(self):
705         # missing explicit is bad
706         self.assert_multi_line_lint(
707             '''class Foo {
708                  Foo(int f);
709                };''',
710             'Single-argument constructors should be marked explicit.'
711             '  [runtime/explicit] [5]')
712         # missing explicit is bad, even with whitespace
713         self.assert_multi_line_lint(
714             '''class Foo {
715                  Foo (int f);
716                };''',
717             ['Extra space before ( in function call  [whitespace/parens] [4]',
718              'Single-argument constructors should be marked explicit.'
719              '  [runtime/explicit] [5]'])
720         # missing explicit, with distracting comment, is still bad
721         self.assert_multi_line_lint(
722             '''class Foo {
723                  Foo(int f);  // simpler than Foo(blargh, blarg)
724                };''',
725             'Single-argument constructors should be marked explicit.'
726             '  [runtime/explicit] [5]')
727         # missing explicit, with qualified classname
728         self.assert_multi_line_lint(
729             '''class Qualifier::AnotherOne::Foo {
730                  Foo(int f);
731                };''',
732             'Single-argument constructors should be marked explicit.'
733             '  [runtime/explicit] [5]')
734         # structs are caught as well.
735         self.assert_multi_line_lint(
736             '''struct Foo {
737                  Foo(int f);
738                };''',
739             'Single-argument constructors should be marked explicit.'
740             '  [runtime/explicit] [5]')
741         # Templatized classes are caught as well.
742         self.assert_multi_line_lint(
743             '''template<typename T> class Foo {
744                  Foo(int f);
745                };''',
746             'Single-argument constructors should be marked explicit.'
747             '  [runtime/explicit] [5]')
748         # proper style is okay
749         self.assert_multi_line_lint(
750             '''class Foo {
751                  explicit Foo(int f);
752                };''',
753             '')
754         # two argument constructor is okay
755         self.assert_multi_line_lint(
756             '''class Foo {
757                  Foo(int f, int b);
758                };''',
759             '')
760         # two argument constructor, across two lines, is okay
761         self.assert_multi_line_lint(
762             '''class Foo {
763                  Foo(int f,
764                      int b);
765                };''',
766             '')
767         # non-constructor (but similar name), is okay
768         self.assert_multi_line_lint(
769             '''class Foo {
770                  aFoo(int f);
771                };''',
772             '')
773         # constructor with void argument is okay
774         self.assert_multi_line_lint(
775             '''class Foo {
776                  Foo(void);
777                };''',
778             '')
779         # single argument method is okay
780         self.assert_multi_line_lint(
781             '''class Foo {
782                  Bar(int b);
783                };''',
784             '')
785         # comments should be ignored
786         self.assert_multi_line_lint(
787             '''class Foo {
788                // Foo(int f);
789                };''',
790             '')
791         # single argument function following class definition is okay
792         # (okay, it's not actually valid, but we don't want a false positive)
793         self.assert_multi_line_lint(
794             '''class Foo {
795                  Foo(int f, int b);
796                };
797                Foo(int f);''',
798             '')
799         # single argument function is okay
800         self.assert_multi_line_lint(
801             '''static Foo(int f);''',
802             '')
803         # single argument copy constructor is okay.
804         self.assert_multi_line_lint(
805             '''class Foo {
806                  Foo(const Foo&);
807                };''',
808             '')
809         self.assert_multi_line_lint(
810             '''class Foo {
811                  Foo(Foo&);
812                };''',
813             '')
814
815     def test_slash_star_comment_on_single_line(self):
816         self.assert_multi_line_lint(
817             '''/* static */ Foo(int f);''',
818             '')
819         self.assert_multi_line_lint(
820             '''/*/ static */  Foo(int f);''',
821             '')
822         self.assert_multi_line_lint(
823             '''/*/ static Foo(int f);''',
824             'Could not find end of multi-line comment'
825             '  [readability/multiline_comment] [5]')
826         self.assert_multi_line_lint(
827             '''    /*/ static Foo(int f);''',
828             'Could not find end of multi-line comment'
829             '  [readability/multiline_comment] [5]')
830         self.assert_multi_line_lint(
831             '''    /**/ static Foo(int f);''',
832             '')
833
834     # Test suspicious usage of "if" like this:
835     # if (a == b) {
836     #   DoSomething();
837     # } if (a == c) {   // Should be "else if".
838     #   DoSomething();  // This gets called twice if a == b && a == c.
839     # }
840     def test_suspicious_usage_of_if(self):
841         self.assert_lint(
842             '    if (a == b) {',
843             '')
844         self.assert_lint(
845             '    } if (a == b) {',
846             'Did you mean "else if"? If not, start a new line for "if".'
847             '  [readability/braces] [4]')
848
849     # Test suspicious usage of memset. Specifically, a 0
850     # as the final argument is almost certainly an error.
851     def test_suspicious_usage_of_memset(self):
852         # Normal use is okay.
853         self.assert_lint(
854             '    memset(buf, 0, sizeof(buf))',
855             '')
856
857         # A 0 as the final argument is almost certainly an error.
858         self.assert_lint(
859             '    memset(buf, sizeof(buf), 0)',
860             'Did you mean "memset(buf, 0, sizeof(buf))"?'
861             '  [runtime/memset] [4]')
862         self.assert_lint(
863             '    memset(buf, xsize * ysize, 0)',
864             'Did you mean "memset(buf, 0, xsize * ysize)"?'
865             '  [runtime/memset] [4]')
866
867         # There is legitimate test code that uses this form.
868         # This is okay since the second argument is a literal.
869         self.assert_lint(
870             "    memset(buf, 'y', 0)",
871             '')
872         self.assert_lint(
873             '    memset(buf, 4, 0)',
874             '')
875         self.assert_lint(
876             '    memset(buf, -1, 0)',
877             '')
878         self.assert_lint(
879             '    memset(buf, 0xF1, 0)',
880             '')
881         self.assert_lint(
882             '    memset(buf, 0xcd, 0)',
883             '')
884
885     def test_check_posix_threading(self):
886         self.assert_lint('sctime_r()', '')
887         self.assert_lint('strtok_r()', '')
888         self.assert_lint('    strtok_r(foo, ba, r)', '')
889         self.assert_lint('brand()', '')
890         self.assert_lint('_rand()', '')
891         self.assert_lint('.rand()', '')
892         self.assert_lint('>rand()', '')
893         self.assert_lint('rand()',
894                          'Consider using rand_r(...) instead of rand(...)'
895                          ' for improved thread safety.'
896                          '  [runtime/threadsafe_fn] [2]')
897         self.assert_lint('strtok()',
898                          'Consider using strtok_r(...) '
899                          'instead of strtok(...)'
900                          ' for improved thread safety.'
901                          '  [runtime/threadsafe_fn] [2]')
902
903     # Test potential format string bugs like printf(foo).
904     def test_format_strings(self):
905         self.assert_lint('printf("foo")', '')
906         self.assert_lint('printf("foo: %s", foo)', '')
907         self.assert_lint('DocidForPrintf(docid)', '')  # Should not trigger.
908         self.assert_lint(
909             'printf(foo)',
910             'Potential format string bug. Do printf("%s", foo) instead.'
911             '  [runtime/printf] [4]')
912         self.assert_lint(
913             'printf(foo.c_str())',
914             'Potential format string bug. '
915             'Do printf("%s", foo.c_str()) instead.'
916             '  [runtime/printf] [4]')
917         self.assert_lint(
918             'printf(foo->c_str())',
919             'Potential format string bug. '
920             'Do printf("%s", foo->c_str()) instead.'
921             '  [runtime/printf] [4]')
922         self.assert_lint(
923             'StringPrintf(foo)',
924             'Potential format string bug. Do StringPrintf("%s", foo) instead.'
925             ''
926             '  [runtime/printf] [4]')
927
928     # Variable-length arrays are not permitted.
929     def test_variable_length_array_detection(self):
930         errmsg = ('Do not use variable-length arrays.  Use an appropriately named '
931                   "('k' followed by CamelCase) compile-time constant for the size."
932                   '  [runtime/arrays] [1]')
933
934         self.assert_lint('int a[any_old_variable];', errmsg)
935         self.assert_lint('int doublesize[some_var * 2];', errmsg)
936         self.assert_lint('int a[afunction()];', errmsg)
937         self.assert_lint('int a[function(kMaxFooBars)];', errmsg)
938         self.assert_lint('bool aList[items_->size()];', errmsg)
939         self.assert_lint('namespace::Type buffer[len+1];', errmsg)
940
941         self.assert_lint('int a[64];', '')
942         self.assert_lint('int a[0xFF];', '')
943         self.assert_lint('int first[256], second[256];', '')
944         self.assert_lint('int arrayName[kCompileTimeConstant];', '')
945         self.assert_lint('char buf[somenamespace::kBufSize];', '')
946         self.assert_lint('int arrayName[ALL_CAPS];', '')
947         self.assert_lint('AClass array1[foo::bar::ALL_CAPS];', '')
948         self.assert_lint('int a[kMaxStrLen + 1];', '')
949         self.assert_lint('int a[sizeof(foo)];', '')
950         self.assert_lint('int a[sizeof(*foo)];', '')
951         self.assert_lint('int a[sizeof foo];', '')
952         self.assert_lint('int a[sizeof(struct Foo)];', '')
953         self.assert_lint('int a[128 - sizeof(const bar)];', '')
954         self.assert_lint('int a[(sizeof(foo) * 4)];', '')
955         self.assert_lint('int a[(arraysize(fixed_size_array)/2) << 1];', 'Missing spaces around /  [whitespace/operators] [3]')
956         self.assert_lint('delete a[some_var];', '')
957         self.assert_lint('return a[some_var];', '')
958
959     # Brace usage
960     def test_braces(self):
961         # Braces shouldn't be followed by a ; unless they're defining a struct
962         # or initializing an array
963         self.assert_lint('int a[3] = { 1, 2, 3 };', '')
964         self.assert_lint(
965             '''const int foo[] =
966                    {1, 2, 3 };''',
967             '')
968         # For single line, unmatched '}' with a ';' is ignored (not enough context)
969         self.assert_multi_line_lint(
970             '''int a[3] = { 1,
971                             2,
972                             3 };''',
973             '')
974         self.assert_multi_line_lint(
975             '''int a[2][3] = { { 1, 2 },
976                              { 3, 4 } };''',
977             '')
978         self.assert_multi_line_lint(
979             '''int a[2][3] =
980                    { { 1, 2 },
981                      { 3, 4 } };''',
982             '')
983
984     # CHECK/EXPECT_TRUE/EXPECT_FALSE replacements
985     def test_check_check(self):
986         self.assert_lint('CHECK(x == 42)',
987                          'Consider using CHECK_EQ instead of CHECK(a == b)'
988                          '  [readability/check] [2]')
989         self.assert_lint('CHECK(x != 42)',
990                          'Consider using CHECK_NE instead of CHECK(a != b)'
991                          '  [readability/check] [2]')
992         self.assert_lint('CHECK(x >= 42)',
993                          'Consider using CHECK_GE instead of CHECK(a >= b)'
994                          '  [readability/check] [2]')
995         self.assert_lint('CHECK(x > 42)',
996                          'Consider using CHECK_GT instead of CHECK(a > b)'
997                          '  [readability/check] [2]')
998         self.assert_lint('CHECK(x <= 42)',
999                          'Consider using CHECK_LE instead of CHECK(a <= b)'
1000                          '  [readability/check] [2]')
1001         self.assert_lint('CHECK(x < 42)',
1002                          'Consider using CHECK_LT instead of CHECK(a < b)'
1003                          '  [readability/check] [2]')
1004
1005         self.assert_lint('DCHECK(x == 42)',
1006                          'Consider using DCHECK_EQ instead of DCHECK(a == b)'
1007                          '  [readability/check] [2]')
1008         self.assert_lint('DCHECK(x != 42)',
1009                          'Consider using DCHECK_NE instead of DCHECK(a != b)'
1010                          '  [readability/check] [2]')
1011         self.assert_lint('DCHECK(x >= 42)',
1012                          'Consider using DCHECK_GE instead of DCHECK(a >= b)'
1013                          '  [readability/check] [2]')
1014         self.assert_lint('DCHECK(x > 42)',
1015                          'Consider using DCHECK_GT instead of DCHECK(a > b)'
1016                          '  [readability/check] [2]')
1017         self.assert_lint('DCHECK(x <= 42)',
1018                          'Consider using DCHECK_LE instead of DCHECK(a <= b)'
1019                          '  [readability/check] [2]')
1020         self.assert_lint('DCHECK(x < 42)',
1021                          'Consider using DCHECK_LT instead of DCHECK(a < b)'
1022                          '  [readability/check] [2]')
1023
1024         self.assert_lint(
1025             'EXPECT_TRUE("42" == x)',
1026             'Consider using EXPECT_EQ instead of EXPECT_TRUE(a == b)'
1027             '  [readability/check] [2]')
1028         self.assert_lint(
1029             'EXPECT_TRUE("42" != x)',
1030             'Consider using EXPECT_NE instead of EXPECT_TRUE(a != b)'
1031             '  [readability/check] [2]')
1032         self.assert_lint(
1033             'EXPECT_TRUE(+42 >= x)',
1034             'Consider using EXPECT_GE instead of EXPECT_TRUE(a >= b)'
1035             '  [readability/check] [2]')
1036         self.assert_lint(
1037             'EXPECT_TRUE_M(-42 > x)',
1038             'Consider using EXPECT_GT_M instead of EXPECT_TRUE_M(a > b)'
1039             '  [readability/check] [2]')
1040         self.assert_lint(
1041             'EXPECT_TRUE_M(42U <= x)',
1042             'Consider using EXPECT_LE_M instead of EXPECT_TRUE_M(a <= b)'
1043             '  [readability/check] [2]')
1044         self.assert_lint(
1045             'EXPECT_TRUE_M(42L < x)',
1046             'Consider using EXPECT_LT_M instead of EXPECT_TRUE_M(a < b)'
1047             '  [readability/check] [2]')
1048
1049         self.assert_lint(
1050             'EXPECT_FALSE(x == 42)',
1051             'Consider using EXPECT_NE instead of EXPECT_FALSE(a == b)'
1052             '  [readability/check] [2]')
1053         self.assert_lint(
1054             'EXPECT_FALSE(x != 42)',
1055             'Consider using EXPECT_EQ instead of EXPECT_FALSE(a != b)'
1056             '  [readability/check] [2]')
1057         self.assert_lint(
1058             'EXPECT_FALSE(x >= 42)',
1059             'Consider using EXPECT_LT instead of EXPECT_FALSE(a >= b)'
1060             '  [readability/check] [2]')
1061         self.assert_lint(
1062             'ASSERT_FALSE(x > 42)',
1063             'Consider using ASSERT_LE instead of ASSERT_FALSE(a > b)'
1064             '  [readability/check] [2]')
1065         self.assert_lint(
1066             'ASSERT_FALSE(x <= 42)',
1067             'Consider using ASSERT_GT instead of ASSERT_FALSE(a <= b)'
1068             '  [readability/check] [2]')
1069         self.assert_lint(
1070             'ASSERT_FALSE_M(x < 42)',
1071             'Consider using ASSERT_GE_M instead of ASSERT_FALSE_M(a < b)'
1072             '  [readability/check] [2]')
1073
1074         self.assert_lint('CHECK(some_iterator == obj.end())', '')
1075         self.assert_lint('EXPECT_TRUE(some_iterator == obj.end())', '')
1076         self.assert_lint('EXPECT_FALSE(some_iterator == obj.end())', '')
1077
1078         self.assert_lint('CHECK(CreateTestFile(dir, (1 << 20)));', '')
1079         self.assert_lint('CHECK(CreateTestFile(dir, (1 >> 20)));', '')
1080
1081         self.assert_lint('CHECK(x<42)',
1082                          ['Missing spaces around <'
1083                           '  [whitespace/operators] [3]',
1084                           'Consider using CHECK_LT instead of CHECK(a < b)'
1085                           '  [readability/check] [2]'])
1086         self.assert_lint('CHECK(x>42)',
1087                          'Consider using CHECK_GT instead of CHECK(a > b)'
1088                          '  [readability/check] [2]')
1089
1090         self.assert_lint(
1091             '    EXPECT_TRUE(42 < x)  // Random comment.',
1092             'Consider using EXPECT_LT instead of EXPECT_TRUE(a < b)'
1093             '  [readability/check] [2]')
1094         self.assert_lint(
1095             'EXPECT_TRUE( 42 < x )',
1096             ['Extra space after ( in function call'
1097              '  [whitespace/parens] [4]',
1098              'Consider using EXPECT_LT instead of EXPECT_TRUE(a < b)'
1099              '  [readability/check] [2]'])
1100         self.assert_lint(
1101             'CHECK("foo" == "foo")',
1102             'Consider using CHECK_EQ instead of CHECK(a == b)'
1103             '  [readability/check] [2]')
1104
1105         self.assert_lint('CHECK_EQ("foo", "foo")', '')
1106
1107     def test_brace_at_begin_of_line(self):
1108         self.assert_lint('{',
1109                          'This { should be at the end of the previous line'
1110                          '  [whitespace/braces] [4]')
1111         self.assert_multi_line_lint(
1112             '#endif\n'
1113             '{\n'
1114             '}\n',
1115             '')
1116         self.assert_multi_line_lint(
1117             'if (condition) {',
1118             '')
1119         self.assert_multi_line_lint(
1120             '    MACRO1(macroArg) {',
1121             '')
1122         self.assert_multi_line_lint(
1123             'ACCESSOR_GETTER(MessageEventPorts) {',
1124             'Place brace on its own line for function definitions.  [whitespace/braces] [4]')
1125         self.assert_multi_line_lint(
1126             'int foo() {',
1127             'Place brace on its own line for function definitions.  [whitespace/braces] [4]')
1128         self.assert_multi_line_lint(
1129             'int foo() const {',
1130             'Place brace on its own line for function definitions.  [whitespace/braces] [4]')
1131         self.assert_multi_line_lint(
1132             'int foo() const\n'
1133             '{\n'
1134             '}\n',
1135             '')
1136         self.assert_multi_line_lint(
1137             'if (condition\n'
1138             '    && condition2\n'
1139             '    && condition3) {\n'
1140             '}\n',
1141             '')
1142
1143     def test_mismatching_spaces_in_parens(self):
1144         self.assert_lint('if (foo ) {', 'Mismatching spaces inside () in if'
1145                          '  [whitespace/parens] [5]')
1146         self.assert_lint('switch ( foo) {', 'Mismatching spaces inside () in switch'
1147                          '  [whitespace/parens] [5]')
1148         self.assert_lint('for (foo; ba; bar ) {', 'Mismatching spaces inside () in for'
1149                          '  [whitespace/parens] [5]')
1150         self.assert_lint('for (; foo; bar) {', '')
1151         self.assert_lint('for ( ; foo; bar) {', '')
1152         self.assert_lint('for ( ; foo; bar ) {', '')
1153         self.assert_lint('for (foo; bar; ) {', '')
1154         self.assert_lint('foreach (foo, foos ) {', 'Mismatching spaces inside () in foreach'
1155                          '  [whitespace/parens] [5]')
1156         self.assert_lint('foreach ( foo, foos) {', 'Mismatching spaces inside () in foreach'
1157                          '  [whitespace/parens] [5]')
1158         self.assert_lint('while (  foo  ) {', 'Should have zero or one spaces inside'
1159                          ' ( and ) in while  [whitespace/parens] [5]')
1160
1161     def test_spacing_for_fncall(self):
1162         self.assert_lint('if (foo) {', '')
1163         self.assert_lint('for (foo;bar;baz) {', '')
1164         self.assert_lint('foreach (foo, foos) {', '')
1165         self.assert_lint('while (foo) {', '')
1166         self.assert_lint('switch (foo) {', '')
1167         self.assert_lint('new (RenderArena()) RenderInline(document())', '')
1168         self.assert_lint('foo( bar)', 'Extra space after ( in function call'
1169                          '  [whitespace/parens] [4]')
1170         self.assert_lint('foobar( \\', '')
1171         self.assert_lint('foobar(     \\', '')
1172         self.assert_lint('( a + b)', 'Extra space after ('
1173                          '  [whitespace/parens] [2]')
1174         self.assert_lint('((a+b))', '')
1175         self.assert_lint('foo (foo)', 'Extra space before ( in function call'
1176                          '  [whitespace/parens] [4]')
1177         self.assert_lint('typedef foo (*foo)(foo)', '')
1178         self.assert_lint('typedef foo (*foo12bar_)(foo)', '')
1179         self.assert_lint('typedef foo (Foo::*bar)(foo)', '')
1180         self.assert_lint('foo (Foo::*bar)(',
1181                          'Extra space before ( in function call'
1182                          '  [whitespace/parens] [4]')
1183         self.assert_lint('typedef foo (Foo::*bar)(', '')
1184         self.assert_lint('(foo)(bar)', '')
1185         self.assert_lint('Foo (*foo)(bar)', '')
1186         self.assert_lint('Foo (*foo)(Bar bar,', '')
1187         self.assert_lint('char (*p)[sizeof(foo)] = &foo', '')
1188         self.assert_lint('char (&ref)[sizeof(foo)] = &foo', '')
1189         self.assert_lint('const char32 (*table[])[6];', '')
1190
1191     def test_spacing_before_braces(self):
1192         self.assert_lint('if (foo){', 'Missing space before {'
1193                          '  [whitespace/braces] [5]')
1194         self.assert_lint('for{', 'Missing space before {'
1195                          '  [whitespace/braces] [5]')
1196         self.assert_lint('for {', '')
1197         self.assert_lint('EXPECT_DEBUG_DEATH({', '')
1198
1199     def test_spacing_around_else(self):
1200         self.assert_lint('}else {', 'Missing space before else'
1201                          '  [whitespace/braces] [5]')
1202         self.assert_lint('} else{', 'Missing space before {'
1203                          '  [whitespace/braces] [5]')
1204         self.assert_lint('} else {', '')
1205         self.assert_lint('} else if', '')
1206
1207     def test_spacing_for_binary_ops(self):
1208         self.assert_lint('if (foo<=bar) {', 'Missing spaces around <='
1209                          '  [whitespace/operators] [3]')
1210         self.assert_lint('if (foo<bar) {', 'Missing spaces around <'
1211                          '  [whitespace/operators] [3]')
1212         self.assert_lint('if (foo<bar->baz) {', 'Missing spaces around <'
1213                          '  [whitespace/operators] [3]')
1214         self.assert_lint('if (foo<bar->bar) {', 'Missing spaces around <'
1215                          '  [whitespace/operators] [3]')
1216         self.assert_lint('typedef hash_map<Foo, Bar', 'Missing spaces around <'
1217                          '  [whitespace/operators] [3]')
1218         self.assert_lint('typedef hash_map<FoooooType, BaaaaarType,', '')
1219         self.assert_lint('a<Foo> t+=b;', 'Missing spaces around +='
1220                          '  [whitespace/operators] [3]')
1221         self.assert_lint('a<Foo> t-=b;', 'Missing spaces around -='
1222                          '  [whitespace/operators] [3]')
1223         self.assert_lint('a<Foo*> t*=b;', 'Missing spaces around *='
1224                          '  [whitespace/operators] [3]')
1225         self.assert_lint('a<Foo*> t/=b;', 'Missing spaces around /='
1226                          '  [whitespace/operators] [3]')
1227         self.assert_lint('a<Foo*> t|=b;', 'Missing spaces around |='
1228                          '  [whitespace/operators] [3]')
1229         self.assert_lint('a<Foo*> t&=b;', 'Missing spaces around &='
1230                          '  [whitespace/operators] [3]')
1231         self.assert_lint('a<Foo*> t<<=b;', 'Missing spaces around <<='
1232                          '  [whitespace/operators] [3]')
1233         self.assert_lint('a<Foo*> t>>=b;', 'Missing spaces around >>='
1234                          '  [whitespace/operators] [3]')
1235         self.assert_lint('a<Foo*> t>>=&b|c;', 'Missing spaces around >>='
1236                          '  [whitespace/operators] [3]')
1237         self.assert_lint('a<Foo*> t<<=*b/c;', 'Missing spaces around <<='
1238                          '  [whitespace/operators] [3]')
1239         self.assert_lint('a<Foo> t -= b;', '')
1240         self.assert_lint('a<Foo> t += b;', '')
1241         self.assert_lint('a<Foo*> t *= b;', '')
1242         self.assert_lint('a<Foo*> t /= b;', '')
1243         self.assert_lint('a<Foo*> t |= b;', '')
1244         self.assert_lint('a<Foo*> t &= b;', '')
1245         self.assert_lint('a<Foo*> t <<= b;', '')
1246         self.assert_lint('a<Foo*> t >>= b;', '')
1247         self.assert_lint('a<Foo*> t >>= &b|c;', 'Missing spaces around |'
1248                          '  [whitespace/operators] [3]')
1249         self.assert_lint('a<Foo*> t <<= *b/c;', 'Missing spaces around /'
1250                          '  [whitespace/operators] [3]')
1251         self.assert_lint('a<Foo*> t <<= b/c; //Test', ['At least two spaces'
1252                          ' is best between code and comments  [whitespace/'
1253                          'comments] [2]', 'Should have a space between // '
1254                          'and comment  [whitespace/comments] [4]', 'Missing'
1255                          ' spaces around /  [whitespace/operators] [3]'])
1256         self.assert_lint('a<Foo*> t <<= b||c;  //Test', ['Should have a space'
1257                          ' between // and comment  [whitespace/comments] [4]',
1258                          'Missing spaces around ||  [whitespace/operators] [3]'])
1259         self.assert_lint('a<Foo*> t <<= b&&c;  // Test', 'Missing spaces around'
1260                          ' &&  [whitespace/operators] [3]')
1261         self.assert_lint('a<Foo*> t <<= b&&&c;  // Test', 'Missing spaces around'
1262                          ' &&  [whitespace/operators] [3]')
1263         self.assert_lint('a<Foo*> t <<= b&&*c;  // Test', 'Missing spaces around'
1264                          ' &&  [whitespace/operators] [3]')
1265         self.assert_lint('a<Foo*> t <<= b && *c;  // Test', '')
1266         self.assert_lint('a<Foo*> t <<= b && &c;  // Test', '')
1267         self.assert_lint('a<Foo*> t <<= b || &c;  /*Test', 'Complex multi-line '
1268                          '/*...*/-style comment found. Lint may give bogus '
1269                          'warnings.  Consider replacing these with //-style'
1270                          ' comments, with #if 0...#endif, or with more clearly'
1271                          ' structured multi-line comments.  [readability/multiline_comment] [5]')
1272         self.assert_lint('a<Foo&> t <<= &b | &c;', '')
1273         self.assert_lint('a<Foo*> t <<= &b & &c;  // Test', '')
1274         self.assert_lint('a<Foo*> t <<= *b / &c;  // Test', '')
1275         self.assert_lint('if (a=b == 1)', 'Missing spaces around =  [whitespace/operators] [4]')
1276         self.assert_lint('a = 1<<20', 'Missing spaces around <<  [whitespace/operators] [3]')
1277         self.assert_lint('if (a = b == 1)', '')
1278         self.assert_lint('a = 1 << 20', '')
1279         self.assert_multi_line_lint('#include "config.h"\n#include <sys/io.h>\n',
1280                                     '')
1281         self.assert_multi_line_lint('#include "config.h"\n#import <foo/bar.h>\n',
1282                                     '')
1283
1284     def test_spacing_before_last_semicolon(self):
1285         self.assert_lint('call_function() ;',
1286                          'Extra space before last semicolon. If this should be an '
1287                          'empty statement, use { } instead.'
1288                          '  [whitespace/semicolon] [5]')
1289         self.assert_lint('while (true) ;',
1290                          'Extra space before last semicolon. If this should be an '
1291                          'empty statement, use { } instead.'
1292                          '  [whitespace/semicolon] [5]')
1293         self.assert_lint('default:;',
1294                          'Semicolon defining empty statement. Use { } instead.'
1295                          '  [whitespace/semicolon] [5]')
1296         self.assert_lint('      ;',
1297                          'Line contains only semicolon. If this should be an empty '
1298                          'statement, use { } instead.'
1299                          '  [whitespace/semicolon] [5]')
1300         self.assert_lint('for (int i = 0; ;', '')
1301
1302     # Static or global STL strings.
1303     def test_static_or_global_stlstrings(self):
1304         self.assert_lint('string foo;',
1305                          'For a static/global string constant, use a C style '
1306                          'string instead: "char foo[]".'
1307                          '  [runtime/string] [4]')
1308         self.assert_lint('string kFoo = "hello";  // English',
1309                          'For a static/global string constant, use a C style '
1310                          'string instead: "char kFoo[]".'
1311                          '  [runtime/string] [4]')
1312         self.assert_lint('static string foo;',
1313                          'For a static/global string constant, use a C style '
1314                          'string instead: "static char foo[]".'
1315                          '  [runtime/string] [4]')
1316         self.assert_lint('static const string foo;',
1317                          'For a static/global string constant, use a C style '
1318                          'string instead: "static const char foo[]".'
1319                          '  [runtime/string] [4]')
1320         self.assert_lint('string Foo::bar;',
1321                          'For a static/global string constant, use a C style '
1322                          'string instead: "char Foo::bar[]".'
1323                          '  [runtime/string] [4]')
1324         # Rare case.
1325         self.assert_lint('string foo("foobar");',
1326                          'For a static/global string constant, use a C style '
1327                          'string instead: "char foo[]".'
1328                          '  [runtime/string] [4]')
1329         # Should not catch local or member variables.
1330         self.assert_lint('    string foo', '')
1331         # Should not catch functions.
1332         self.assert_lint('string EmptyString() { return ""; }', '')
1333         self.assert_lint('string EmptyString () { return ""; }', '')
1334         self.assert_lint('string VeryLongNameFunctionSometimesEndsWith(\n'
1335                          '    VeryLongNameType very_long_name_variable) {}', '')
1336         self.assert_lint('template<>\n'
1337                          'string FunctionTemplateSpecialization<SomeType>(\n'
1338                          '      int x) { return ""; }', '')
1339         self.assert_lint('template<>\n'
1340                          'string FunctionTemplateSpecialization<vector<A::B>* >(\n'
1341                          '      int x) { return ""; }', '')
1342
1343         # should not catch methods of template classes.
1344         self.assert_lint('string Class<Type>::Method() const\n'
1345                          '{\n'
1346                          '  return "";\n'
1347                          '}\n', '')
1348         self.assert_lint('string Class<Type>::Method(\n'
1349                          '   int arg) const\n'
1350                          '{\n'
1351                          '  return "";\n'
1352                          '}\n', '')
1353
1354     def test_no_spaces_in_function_calls(self):
1355         self.assert_lint('TellStory(1, 3);',
1356                          '')
1357         self.assert_lint('TellStory(1, 3 );',
1358                          'Extra space before )'
1359                          '  [whitespace/parens] [2]')
1360         self.assert_lint('TellStory(1 /* wolf */, 3 /* pigs */);',
1361                          '')
1362         self.assert_multi_line_lint('#endif\n    );',
1363                                     '')
1364
1365     def test_two_spaces_between_code_and_comments(self):
1366         self.assert_lint('} // namespace foo',
1367                          'At least two spaces is best between code and comments'
1368                          '  [whitespace/comments] [2]')
1369         self.assert_lint('}// namespace foo',
1370                          'At least two spaces is best between code and comments'
1371                          '  [whitespace/comments] [2]')
1372         self.assert_lint('printf("foo"); // Outside quotes.',
1373                          'At least two spaces is best between code and comments'
1374                          '  [whitespace/comments] [2]')
1375         self.assert_lint('int i = 0;  // Having two spaces is fine.', '')
1376         self.assert_lint('int i = 0;   // Having three spaces is OK.', '')
1377         self.assert_lint('// Top level comment', '')
1378         self.assert_lint('    // Line starts with four spaces.', '')
1379         self.assert_lint('foo();\n'
1380                          '{ // A scope is opening.', '')
1381         self.assert_lint('    foo();\n'
1382                          '    { // An indented scope is opening.', '')
1383         self.assert_lint('if (foo) { // not a pure scope; comment is too close!',
1384                          'At least two spaces is best between code and comments'
1385                          '  [whitespace/comments] [2]')
1386         self.assert_lint('printf("// In quotes.")', '')
1387         self.assert_lint('printf("\\"%s // In quotes.")', '')
1388         self.assert_lint('printf("%s", "// In quotes.")', '')
1389
1390     def test_space_after_comment_marker(self):
1391         self.assert_lint('//', '')
1392         self.assert_lint('//x', 'Should have a space between // and comment'
1393                          '  [whitespace/comments] [4]')
1394         self.assert_lint('// x', '')
1395         self.assert_lint('//----', '')
1396         self.assert_lint('//====', '')
1397         self.assert_lint('//////', '')
1398         self.assert_lint('////// x', '')
1399         self.assert_lint('/// x', '')
1400         self.assert_lint('////x', 'Should have a space between // and comment'
1401                          '  [whitespace/comments] [4]')
1402
1403     def test_newline_at_eof(self):
1404         def do_test(self, data, is_missing_eof):
1405             error_collector = ErrorCollector(self.assert_)
1406             cpp_style.process_file_data('foo.cpp', 'cpp', data.split('\n'),
1407                                         error_collector)
1408             # The warning appears only once.
1409             self.assertEquals(
1410                 int(is_missing_eof),
1411                 error_collector.results().count(
1412                     'Could not find a newline character at the end of the file.'
1413                     '  [whitespace/ending_newline] [5]'))
1414
1415         do_test(self, '// Newline\n// at EOF\n', False)
1416         do_test(self, '// No newline\n// at EOF', True)
1417
1418     def test_invalid_utf8(self):
1419         def do_test(self, raw_bytes, has_invalid_utf8):
1420             error_collector = ErrorCollector(self.assert_)
1421             cpp_style.process_file_data(
1422                 'foo.cpp', 'cpp',
1423                 unicode(raw_bytes, 'utf8', 'replace').split('\n'),
1424                 error_collector)
1425             # The warning appears only once.
1426             self.assertEquals(
1427                 int(has_invalid_utf8),
1428                 error_collector.results().count(
1429                     'Line contains invalid UTF-8'
1430                     ' (or Unicode replacement character).'
1431                     '  [readability/utf8] [5]'))
1432
1433         do_test(self, 'Hello world\n', False)
1434         do_test(self, '\xe9\x8e\xbd\n', False)
1435         do_test(self, '\xe9x\x8e\xbd\n', True)
1436         # This is the encoding of the replacement character itself (which
1437         # you can see by evaluating codecs.getencoder('utf8')(u'\ufffd')).
1438         do_test(self, '\xef\xbf\xbd\n', True)
1439
1440     def test_is_blank_line(self):
1441         self.assert_(cpp_style.is_blank_line(''))
1442         self.assert_(cpp_style.is_blank_line(' '))
1443         self.assert_(cpp_style.is_blank_line(' \t\r\n'))
1444         self.assert_(not cpp_style.is_blank_line('int a;'))
1445         self.assert_(not cpp_style.is_blank_line('{'))
1446
1447     def test_blank_lines_check(self):
1448         self.assert_blank_lines_check(['{\n', '\n', '\n', '}\n'], 1, 1)
1449         self.assert_blank_lines_check(['  if (foo) {\n', '\n', '  }\n'], 1, 1)
1450         self.assert_blank_lines_check(
1451             ['\n', '// {\n', '\n', '\n', '// Comment\n', '{\n', '}\n'], 0, 0)
1452         self.assert_blank_lines_check(['\n', 'run("{");\n', '\n'], 0, 0)
1453         self.assert_blank_lines_check(['\n', '  if (foo) { return 0; }\n', '\n'], 0, 0)
1454
1455     def test_allow_blank_line_before_closing_namespace(self):
1456         error_collector = ErrorCollector(self.assert_)
1457         cpp_style.process_file_data('foo.cpp', 'cpp',
1458                                     ['namespace {', '', '}  // namespace'],
1459                                     error_collector)
1460         self.assertEquals(0, error_collector.results().count(
1461             'Blank line at the end of a code block.  Is this needed?'
1462             '  [whitespace/blank_line] [3]'))
1463
1464     def test_allow_blank_line_before_if_else_chain(self):
1465         error_collector = ErrorCollector(self.assert_)
1466         cpp_style.process_file_data('foo.cpp', 'cpp',
1467                                     ['if (hoge) {',
1468                                      '',  # No warning
1469                                      '} else if (piyo) {',
1470                                      '',  # No warning
1471                                      '} else if (piyopiyo) {',
1472                                      '  hoge = true;',  # No warning
1473                                      '} else {',
1474                                      '',  # Warning on this line
1475                                      '}'],
1476                                     error_collector)
1477         self.assertEquals(1, error_collector.results().count(
1478             'Blank line at the end of a code block.  Is this needed?'
1479             '  [whitespace/blank_line] [3]'))
1480
1481     def test_else_on_same_line_as_closing_braces(self):
1482         error_collector = ErrorCollector(self.assert_)
1483         cpp_style.process_file_data('foo.cpp', 'cpp',
1484                                     ['if (hoge) {',
1485                                      '',
1486                                      '}',
1487                                      ' else {'  # Warning on this line
1488                                      '',
1489                                      '}'],
1490                                     error_collector)
1491         self.assertEquals(1, error_collector.results().count(
1492             'An else should appear on the same line as the preceding }'
1493             '  [whitespace/newline] [4]'))
1494
1495     def test_else_clause_not_on_same_line_as_else(self):
1496         self.assert_lint('    else DoSomethingElse();',
1497                          'Else clause should never be on same line as else '
1498                          '(use 2 lines)  [whitespace/newline] [4]')
1499         self.assert_lint('    else ifDoSomethingElse();',
1500                          'Else clause should never be on same line as else '
1501                          '(use 2 lines)  [whitespace/newline] [4]')
1502         self.assert_lint('    else if (blah) {', '')
1503         self.assert_lint('    variable_ends_in_else = true;', '')
1504
1505     def test_comma(self):
1506         self.assert_lint('a = f(1,2);',
1507                          'Missing space after ,  [whitespace/comma] [3]')
1508         self.assert_lint('int tmp=a,a=b,b=tmp;',
1509                          ['Missing spaces around =  [whitespace/operators] [4]',
1510                           'Missing space after ,  [whitespace/comma] [3]'])
1511         self.assert_lint('f(a, /* name */ b);', '')
1512         self.assert_lint('f(a, /* name */b);', '')
1513
1514     def test_pointer_reference_marker_location(self):
1515         self.assert_lint('int* b;', '', 'foo.cpp')
1516         self.assert_lint('int *b;',
1517                          'Declaration has space between type name and * in int *b  [whitespace/declaration] [3]',
1518                          'foo.cpp')
1519         self.assert_lint('return *b;', '', 'foo.cpp')
1520         self.assert_lint('int *b;', '', 'foo.c')
1521         self.assert_lint('int* b;',
1522                          'Declaration has space between * and variable name in int* b  [whitespace/declaration] [3]',
1523                          'foo.c')
1524         self.assert_lint('int& b;', '', 'foo.cpp')
1525         self.assert_lint('int &b;',
1526                          'Declaration has space between type name and & in int &b  [whitespace/declaration] [3]',
1527                          'foo.cpp')
1528         self.assert_lint('return &b;', '', 'foo.cpp')
1529
1530     def test_indent(self):
1531         self.assert_lint('static int noindent;', '')
1532         self.assert_lint('    int fourSpaceIndent;', '')
1533         self.assert_lint(' int oneSpaceIndent;',
1534                          'Weird number of spaces at line-start.  '
1535                          'Are you using a 4-space indent?  [whitespace/indent] [3]')
1536         self.assert_lint('   int threeSpaceIndent;',
1537                          'Weird number of spaces at line-start.  '
1538                          'Are you using a 4-space indent?  [whitespace/indent] [3]')
1539         self.assert_lint(' char* oneSpaceIndent = "public:";',
1540                          'Weird number of spaces at line-start.  '
1541                          'Are you using a 4-space indent?  [whitespace/indent] [3]')
1542         self.assert_lint(' public:', '')
1543         self.assert_lint('  public:', '')
1544         self.assert_lint('   public:', '')
1545
1546     def test_label(self):
1547         self.assert_lint('public:',
1548                          'Labels should always be indented at least one space.  '
1549                          'If this is a member-initializer list in a constructor, '
1550                          'the colon should be on the line after the definition '
1551                          'header.  [whitespace/labels] [4]')
1552         self.assert_lint('  public:', '')
1553         self.assert_lint('   public:', '')
1554         self.assert_lint(' public:', '')
1555         self.assert_lint('  public:', '')
1556         self.assert_lint('   public:', '')
1557
1558     def test_not_alabel(self):
1559         self.assert_lint('MyVeryLongNamespace::MyVeryLongClassName::', '')
1560
1561     def test_tab(self):
1562         self.assert_lint('\tint a;',
1563                          'Tab found; better to use spaces  [whitespace/tab] [1]')
1564         self.assert_lint('int a = 5;\t\t// set a to 5',
1565                          'Tab found; better to use spaces  [whitespace/tab] [1]')
1566
1567     def test_parse_arguments(self):
1568         old_usage = cpp_style._USAGE
1569         old_style_categories = cpp_style._STYLE_CATEGORIES
1570         old_webkit_filter_rules = cpp_style._WEBKIT_FILTER_RULES
1571         old_output_format = cpp_style._cpp_style_state.output_format
1572         old_verbose_level = cpp_style._cpp_style_state.verbose_level
1573         old_filters = cpp_style._cpp_style_state.filters
1574         try:
1575             # Don't print usage during the tests, or filter categories
1576             cpp_style._USAGE = ''
1577             cpp_style._STYLE_CATEGORIES = []
1578             cpp_style._WEBKIT_FILTER_RULES = []
1579
1580             self.assertRaises(SystemExit, cpp_style.parse_arguments, ['--badopt'])
1581             self.assertRaises(SystemExit, cpp_style.parse_arguments, ['--help'])
1582             self.assertRaises(SystemExit, cpp_style.parse_arguments, ['--filter='])
1583             # This is illegal because all filters must start with + or -
1584             self.assertRaises(ValueError, cpp_style.parse_arguments, ['--filter=foo'])
1585             self.assertRaises(ValueError, cpp_style.parse_arguments,
1586                               ['--filter=+a,b,-c'])
1587
1588             self.assertEquals((['foo.cpp'], {}), cpp_style.parse_arguments(['foo.cpp']))
1589             self.assertEquals(old_output_format, cpp_style._cpp_style_state.output_format)
1590             self.assertEquals(old_verbose_level, cpp_style._cpp_style_state.verbose_level)
1591
1592             self.assertEquals(([], {}), cpp_style.parse_arguments([]))
1593             self.assertEquals(([], {}), cpp_style.parse_arguments(['--v=0']))
1594
1595             self.assertEquals((['foo.cpp'], {}),
1596                               cpp_style.parse_arguments(['--v=1', 'foo.cpp']))
1597             self.assertEquals(1, cpp_style._cpp_style_state.verbose_level)
1598             self.assertEquals((['foo.h'], {}),
1599                               cpp_style.parse_arguments(['--v=3', 'foo.h']))
1600             self.assertEquals(3, cpp_style._cpp_style_state.verbose_level)
1601             self.assertEquals((['foo.cpp'], {}),
1602                               cpp_style.parse_arguments(['--verbose=5', 'foo.cpp']))
1603             self.assertEquals(5, cpp_style._cpp_style_state.verbose_level)
1604             self.assertRaises(ValueError,
1605                               cpp_style.parse_arguments, ['--v=f', 'foo.cpp'])
1606
1607             self.assertEquals((['foo.cpp'], {}),
1608                               cpp_style.parse_arguments(['--output=emacs', 'foo.cpp']))
1609             self.assertEquals('emacs', cpp_style._cpp_style_state.output_format)
1610             self.assertEquals((['foo.h'], {}),
1611                               cpp_style.parse_arguments(['--output=vs7', 'foo.h']))
1612             self.assertEquals('vs7', cpp_style._cpp_style_state.output_format)
1613             self.assertRaises(SystemExit,
1614                               cpp_style.parse_arguments, ['--output=blah', 'foo.cpp'])
1615
1616             filt = '-,+whitespace,-whitespace/indent'
1617             self.assertEquals((['foo.h'], {}),
1618                               cpp_style.parse_arguments(['--filter='+filt, 'foo.h']))
1619             self.assertEquals(['-', '+whitespace', '-whitespace/indent'],
1620                               cpp_style._cpp_style_state.filters)
1621
1622             self.assertEquals((['foo.cpp', 'foo.h'], {}),
1623                               cpp_style.parse_arguments(['foo.cpp', 'foo.h']))
1624
1625             self.assertEquals((['foo.cpp'], {'--foo': ''}),
1626                               cpp_style.parse_arguments(['--foo', 'foo.cpp'], ['foo']))
1627             self.assertEquals((['foo.cpp'], {'--foo': 'bar'}),
1628                               cpp_style.parse_arguments(['--foo=bar', 'foo.cpp'], ['foo=']))
1629             self.assertEquals((['foo.cpp'], {}),
1630                               cpp_style.parse_arguments(['foo.cpp'], ['foo=']))
1631             self.assertRaises(SystemExit,
1632                               cpp_style.parse_arguments,
1633                               ['--footypo=bar', 'foo.cpp'], ['foo='])
1634         finally:
1635             cpp_style._USAGE = old_usage
1636             cpp_style._STYLE_CATEGORIES = old_style_categories
1637             cpp_style._WEBKIT_FILTER_RULES = old_webkit_filter_rules
1638             cpp_style._cpp_style_state.output_format = old_output_format
1639             cpp_style._cpp_style_state.verbose_level = old_verbose_level
1640             cpp_style._cpp_style_state.filters = old_filters
1641
1642     def test_filter(self):
1643         old_filters = cpp_style._cpp_style_state.filters
1644         try:
1645             cpp_style._cpp_style_state.set_filters('-,+whitespace,-whitespace/indent')
1646             self.assert_lint(
1647                 '// Hello there ',
1648                 'Line ends in whitespace.  Consider deleting these extra spaces.'
1649                 '  [whitespace/end_of_line] [4]')
1650             self.assert_lint('int a = (int)1.0;', '')
1651             self.assert_lint(' weird opening space', '')
1652         finally:
1653             cpp_style._cpp_style_state.filters = old_filters
1654
1655     def test_default_filter(self):
1656         default_filter_rules = cpp_style._DEFAULT_FILTER_RULES
1657         old_filters = cpp_style._cpp_style_state.filters
1658         cpp_style._DEFAULT_FILTER_RULES = [ '-whitespace' ]
1659         try:
1660             # Reset filters
1661             cpp_style._cpp_style_state.set_filters('')
1662             self.assert_lint('// Hello there ', '')
1663             cpp_style._cpp_style_state.set_filters('+whitespace/end_of_line')
1664             self.assert_lint(
1665                 '// Hello there ',
1666                 'Line ends in whitespace.  Consider deleting these extra spaces.'
1667                 '  [whitespace/end_of_line] [4]')
1668             self.assert_lint(' weird opening space', '')
1669         finally:
1670             cpp_style._cpp_style_state.filters = old_filters
1671             cpp_style._DEFAULT_FILTER_RULES = default_filter_rules
1672
1673     def test_unnamed_namespaces_in_headers(self):
1674         self.assert_language_rules_check(
1675             'foo.h', 'namespace {',
1676             'Do not use unnamed namespaces in header files.  See'
1677             ' http://google-styleguide.googlecode.com/svn/trunk/cppguide.xml#Namespaces'
1678             ' for more information.  [build/namespaces] [4]')
1679         # namespace registration macros are OK.
1680         self.assert_language_rules_check('foo.h', 'namespace {  \\', '')
1681         # named namespaces are OK.
1682         self.assert_language_rules_check('foo.h', 'namespace foo {', '')
1683         self.assert_language_rules_check('foo.h', 'namespace foonamespace {', '')
1684         self.assert_language_rules_check('foo.cpp', 'namespace {', '')
1685         self.assert_language_rules_check('foo.cpp', 'namespace foo {', '')
1686
1687     def test_build_class(self):
1688         # Test that the linter can parse to the end of class definitions,
1689         # and that it will report when it can't.
1690         # Use multi-line linter because it performs the ClassState check.
1691         self.assert_multi_line_lint(
1692             'class Foo {',
1693             'Failed to find complete declaration of class Foo'
1694             '  [build/class] [5]')
1695         # Don't warn on forward declarations of various types.
1696         self.assert_multi_line_lint(
1697             'class Foo;',
1698             '')
1699         self.assert_multi_line_lint(
1700             '''struct Foo*
1701                  foo = NewFoo();''',
1702             '')
1703         # Here is an example where the linter gets confused, even though
1704         # the code doesn't violate the style guide.
1705         self.assert_multi_line_lint(
1706             '''class Foo
1707             #ifdef DERIVE_FROM_GOO
1708               : public Goo {
1709             #else
1710               : public Hoo {
1711             #endif
1712               };''',
1713             'Failed to find complete declaration of class Foo'
1714             '  [build/class] [5]')
1715
1716     def test_build_end_comment(self):
1717         # The crosstool compiler we currently use will fail to compile the
1718         # code in this test, so we might consider removing the lint check.
1719         self.assert_lint('#endif Not a comment',
1720                          'Uncommented text after #endif is non-standard.'
1721                          '  Use a comment.'
1722                          '  [build/endif_comment] [5]')
1723
1724     def test_build_forward_decl(self):
1725         # The crosstool compiler we currently use will fail to compile the
1726         # code in this test, so we might consider removing the lint check.
1727         self.assert_lint('class Foo::Goo;',
1728                          'Inner-style forward declarations are invalid.'
1729                          '  Remove this line.'
1730                          '  [build/forward_decl] [5]')
1731
1732     def test_build_header_guard(self):
1733         file_path = 'mydir/foo.h'
1734
1735         # We can't rely on our internal stuff to get a sane path on the open source
1736         # side of things, so just parse out the suggested header guard. This
1737         # doesn't allow us to test the suggested header guard, but it does let us
1738         # test all the other header tests.
1739         error_collector = ErrorCollector(self.assert_)
1740         cpp_style.process_file_data(file_path, 'h', [], error_collector)
1741         expected_guard = ''
1742         matcher = re.compile(
1743             'No \#ifndef header guard found\, suggested CPP variable is\: ([A-Z_0-9]+) ')
1744         for error in error_collector.result_list():
1745             matches = matcher.match(error)
1746             if matches:
1747                 expected_guard = matches.group(1)
1748                 break
1749
1750         # Make sure we extracted something for our header guard.
1751         self.assertNotEqual(expected_guard, '')
1752
1753         # Wrong guard
1754         error_collector = ErrorCollector(self.assert_)
1755         cpp_style.process_file_data(file_path, 'h',
1756                                     ['#ifndef FOO_H', '#define FOO_H'], error_collector)
1757         self.assertEquals(
1758             1,
1759             error_collector.result_list().count(
1760                 '#ifndef header guard has wrong style, please use: %s'
1761                 '  [build/header_guard] [5]' % expected_guard),
1762             error_collector.result_list())
1763
1764         # No define
1765         error_collector = ErrorCollector(self.assert_)
1766         cpp_style.process_file_data(file_path, 'h',
1767                                     ['#ifndef %s' % expected_guard], error_collector)
1768         self.assertEquals(
1769             1,
1770             error_collector.result_list().count(
1771                 'No #ifndef header guard found, suggested CPP variable is: %s'
1772                 '  [build/header_guard] [5]' % expected_guard),
1773             error_collector.result_list())
1774
1775         # Mismatched define
1776         error_collector = ErrorCollector(self.assert_)
1777         cpp_style.process_file_data(file_path, 'h',
1778                                     ['#ifndef %s' % expected_guard,
1779                                      '#define FOO_H'],
1780                                     error_collector)
1781         self.assertEquals(
1782             1,
1783             error_collector.result_list().count(
1784                 'No #ifndef header guard found, suggested CPP variable is: %s'
1785                 '  [build/header_guard] [5]' % expected_guard),
1786             error_collector.result_list())
1787
1788         # No endif
1789         error_collector = ErrorCollector(self.assert_)
1790         cpp_style.process_file_data(file_path, 'h',
1791                                     ['#ifndef %s' % expected_guard,
1792                                      '#define %s' % expected_guard],
1793                                     error_collector)
1794         self.assertEquals(
1795             1,
1796             error_collector.result_list().count(
1797                 '#endif line should be "#endif  // %s"'
1798                 '  [build/header_guard] [5]' % expected_guard),
1799             error_collector.result_list())
1800
1801         # Commentless endif
1802         error_collector = ErrorCollector(self.assert_)
1803         cpp_style.process_file_data(file_path, 'h',
1804                                     ['#ifndef %s' % expected_guard,
1805                                      '#define %s' % expected_guard,
1806                                      '#endif'],
1807                                     error_collector)
1808         self.assertEquals(
1809             1,
1810             error_collector.result_list().count(
1811                 '#endif line should be "#endif  // %s"'
1812                 '  [build/header_guard] [5]' % expected_guard),
1813             error_collector.result_list())
1814
1815         # Commentless endif for old-style guard
1816         error_collector = ErrorCollector(self.assert_)
1817         cpp_style.process_file_data(file_path, 'h',
1818                                     ['#ifndef %s_' % expected_guard,
1819                                      '#define %s_' % expected_guard,
1820                                      '#endif'],
1821                                     error_collector)
1822         self.assertEquals(
1823             1,
1824             error_collector.result_list().count(
1825                 '#endif line should be "#endif  // %s"'
1826                 '  [build/header_guard] [5]' % expected_guard),
1827             error_collector.result_list())
1828
1829         # No header guard errors
1830         error_collector = ErrorCollector(self.assert_)
1831         cpp_style.process_file_data(file_path, 'h',
1832                                     ['#ifndef %s' % expected_guard,
1833                                      '#define %s' % expected_guard,
1834                                      '#endif  // %s' % expected_guard],
1835                                     error_collector)
1836         for line in error_collector.result_list():
1837             if line.find('build/header_guard') != -1:
1838                 self.fail('Unexpected error: %s' % line)
1839
1840         # No header guard errors for old-style guard
1841         error_collector = ErrorCollector(self.assert_)
1842         cpp_style.process_file_data(file_path, 'h',
1843                                     ['#ifndef %s_' % expected_guard,
1844                                      '#define %s_' % expected_guard,
1845                                      '#endif  // %s_' % expected_guard],
1846                                     error_collector)
1847         for line in error_collector.result_list():
1848             if line.find('build/header_guard') != -1:
1849                 self.fail('Unexpected error: %s' % line)
1850
1851         old_verbose_level = cpp_style._cpp_style_state.verbose_level
1852         try:
1853             cpp_style._cpp_style_state.verbose_level = 0
1854             # Warn on old-style guard if verbosity is 0.
1855             error_collector = ErrorCollector(self.assert_)
1856             cpp_style.process_file_data(file_path, 'h',
1857                                         ['#ifndef %s_' % expected_guard,
1858                                          '#define %s_' % expected_guard,
1859                                          '#endif  // %s_' % expected_guard],
1860                                         error_collector)
1861             self.assertEquals(
1862                 1,
1863                 error_collector.result_list().count(
1864                     '#ifndef header guard has wrong style, please use: %s'
1865                     '  [build/header_guard] [0]' % expected_guard),
1866                 error_collector.result_list())
1867         finally:
1868             cpp_style._cpp_style_state.verbose_level = old_verbose_level
1869
1870         # Completely incorrect header guard
1871         error_collector = ErrorCollector(self.assert_)
1872         cpp_style.process_file_data(file_path, 'h',
1873                                     ['#ifndef FOO',
1874                                      '#define FOO',
1875                                      '#endif  // FOO'],
1876                                     error_collector)
1877         self.assertEquals(
1878             1,
1879             error_collector.result_list().count(
1880                 '#ifndef header guard has wrong style, please use: %s'
1881                 '  [build/header_guard] [5]' % expected_guard),
1882             error_collector.result_list())
1883         self.assertEquals(
1884             1,
1885             error_collector.result_list().count(
1886                 '#endif line should be "#endif  // %s"'
1887                 '  [build/header_guard] [5]' % expected_guard),
1888             error_collector.result_list())
1889
1890     def test_build_printf_format(self):
1891         self.assert_lint(
1892             r'printf("\%%d", value);',
1893             '%, [, (, and { are undefined character escapes.  Unescape them.'
1894             '  [build/printf_format] [3]')
1895
1896         self.assert_lint(
1897             r'snprintf(buffer, sizeof(buffer), "\[%d", value);',
1898             '%, [, (, and { are undefined character escapes.  Unescape them.'
1899             '  [build/printf_format] [3]')
1900
1901         self.assert_lint(
1902             r'fprintf(file, "\(%d", value);',
1903             '%, [, (, and { are undefined character escapes.  Unescape them.'
1904             '  [build/printf_format] [3]')
1905
1906         self.assert_lint(
1907             r'vsnprintf(buffer, sizeof(buffer), "\\\{%d", ap);',
1908             '%, [, (, and { are undefined character escapes.  Unescape them.'
1909             '  [build/printf_format] [3]')
1910
1911         # Don't warn if double-slash precedes the symbol
1912         self.assert_lint(r'printf("\\%%%d", value);',
1913                          '')
1914
1915     def test_runtime_printf_format(self):
1916         self.assert_lint(
1917             r'fprintf(file, "%q", value);',
1918             '%q in format strings is deprecated.  Use %ll instead.'
1919             '  [runtime/printf_format] [3]')
1920
1921         self.assert_lint(
1922             r'aprintf(file, "The number is %12q", value);',
1923             '%q in format strings is deprecated.  Use %ll instead.'
1924             '  [runtime/printf_format] [3]')
1925
1926         self.assert_lint(
1927             r'printf(file, "The number is" "%-12q", value);',
1928             '%q in format strings is deprecated.  Use %ll instead.'
1929             '  [runtime/printf_format] [3]')
1930
1931         self.assert_lint(
1932             r'printf(file, "The number is" "%+12q", value);',
1933             '%q in format strings is deprecated.  Use %ll instead.'
1934             '  [runtime/printf_format] [3]')
1935
1936         self.assert_lint(
1937             r'printf(file, "The number is" "% 12q", value);',
1938             '%q in format strings is deprecated.  Use %ll instead.'
1939             '  [runtime/printf_format] [3]')
1940
1941         self.assert_lint(
1942             r'snprintf(file, "Never mix %d and %1$d parmaeters!", value);',
1943             '%N$ formats are unconventional.  Try rewriting to avoid them.'
1944             '  [runtime/printf_format] [2]')
1945
1946     def assert_lintLogCodeOnError(self, code, expected_message):
1947         # Special assert_lint which logs the input code on error.
1948         result = self.perform_single_line_lint(code, 'foo.cpp')
1949         if result != expected_message:
1950             self.fail('For code: "%s"\nGot: "%s"\nExpected: "%s"'
1951                       % (code, result, expected_message))
1952
1953     def test_build_storage_class(self):
1954         qualifiers = [None, 'const', 'volatile']
1955         signs = [None, 'signed', 'unsigned']
1956         types = ['void', 'char', 'int', 'float', 'double',
1957                  'schar', 'int8', 'uint8', 'int16', 'uint16',
1958                  'int32', 'uint32', 'int64', 'uint64']
1959         storage_classes = ['auto', 'extern', 'register', 'static', 'typedef']
1960
1961         build_storage_class_error_message = (
1962             'Storage class (static, extern, typedef, etc) should be first.'
1963             '  [build/storage_class] [5]')
1964
1965         # Some explicit cases. Legal in C++, deprecated in C99.
1966         self.assert_lint('const int static foo = 5;',
1967                          build_storage_class_error_message)
1968
1969         self.assert_lint('char static foo;',
1970                          build_storage_class_error_message)
1971
1972         self.assert_lint('double const static foo = 2.0;',
1973                          build_storage_class_error_message)
1974
1975         self.assert_lint('uint64 typedef unsignedLongLong;',
1976                          build_storage_class_error_message)
1977
1978         self.assert_lint('int register foo = 0;',
1979                          build_storage_class_error_message)
1980
1981         # Since there are a very large number of possibilities, randomly
1982         # construct declarations.
1983         # Make sure that the declaration is logged if there's an error.
1984         # Seed generator with an integer for absolute reproducibility.
1985         random.seed(25)
1986         for unused_i in range(10):
1987             # Build up random list of non-storage-class declaration specs.
1988             other_decl_specs = [random.choice(qualifiers), random.choice(signs),
1989                                 random.choice(types)]
1990             # remove None
1991             other_decl_specs = filter(lambda x: x is not None, other_decl_specs)
1992
1993             # shuffle
1994             random.shuffle(other_decl_specs)
1995
1996             # insert storage class after the first
1997             storage_class = random.choice(storage_classes)
1998             insertion_point = random.randint(1, len(other_decl_specs))
1999             decl_specs = (other_decl_specs[0:insertion_point]
2000                           + [storage_class]
2001                           + other_decl_specs[insertion_point:])
2002
2003             self.assert_lintLogCodeOnError(
2004                 ' '.join(decl_specs) + ';',
2005                 build_storage_class_error_message)
2006
2007             # but no error if storage class is first
2008             self.assert_lintLogCodeOnError(
2009                 storage_class + ' ' + ' '.join(other_decl_specs),
2010                 '')
2011
2012     def test_legal_copyright(self):
2013         legal_copyright_message = (
2014             'No copyright message found.  '
2015             'You should have a line: "Copyright [year] <Copyright Owner>"'
2016             '  [legal/copyright] [5]')
2017
2018         copyright_line = '// Copyright 2008 Google Inc. All Rights Reserved.'
2019
2020         file_path = 'mydir/googleclient/foo.cpp'
2021
2022         # There should be a copyright message in the first 10 lines
2023         error_collector = ErrorCollector(self.assert_)
2024         cpp_style.process_file_data(file_path, 'cpp', [], error_collector)
2025         self.assertEquals(
2026             1,
2027             error_collector.result_list().count(legal_copyright_message))
2028
2029         error_collector = ErrorCollector(self.assert_)
2030         cpp_style.process_file_data(
2031             file_path, 'cpp',
2032             ['' for unused_i in range(10)] + [copyright_line],
2033             error_collector)
2034         self.assertEquals(
2035             1,
2036             error_collector.result_list().count(legal_copyright_message))
2037
2038         # Test that warning isn't issued if Copyright line appears early enough.
2039         error_collector = ErrorCollector(self.assert_)
2040         cpp_style.process_file_data(file_path, 'cpp', [copyright_line], error_collector)
2041         for message in error_collector.result_list():
2042             if message.find('legal/copyright') != -1:
2043                 self.fail('Unexpected error: %s' % message)
2044
2045         error_collector = ErrorCollector(self.assert_)
2046         cpp_style.process_file_data(
2047             file_path, 'cpp',
2048             ['' for unused_i in range(9)] + [copyright_line],
2049             error_collector)
2050         for message in error_collector.result_list():
2051             if message.find('legal/copyright') != -1:
2052                 self.fail('Unexpected error: %s' % message)
2053
2054     def test_invalid_increment(self):
2055         self.assert_lint('*count++;',
2056                          'Changing pointer instead of value (or unused value of '
2057                          'operator*).  [runtime/invalid_increment] [5]')
2058
2059
2060 class CleansedLinesTest(unittest.TestCase):
2061     def test_init(self):
2062         lines = ['Line 1',
2063                  'Line 2',
2064                  'Line 3 // Comment test',
2065                  'Line 4 "foo"']
2066
2067         clean_lines = cpp_style.CleansedLines(lines)
2068         self.assertEquals(lines, clean_lines.raw_lines)
2069         self.assertEquals(4, clean_lines.num_lines())
2070
2071         self.assertEquals(['Line 1',
2072                            'Line 2',
2073                            'Line 3 ',
2074                            'Line 4 "foo"'],
2075                           clean_lines.lines)
2076
2077         self.assertEquals(['Line 1',
2078                            'Line 2',
2079                            'Line 3 ',
2080                            'Line 4 ""'],
2081                           clean_lines.elided)
2082
2083     def test_init_empty(self):
2084         clean_lines = cpp_style.CleansedLines([])
2085         self.assertEquals([], clean_lines.raw_lines)
2086         self.assertEquals(0, clean_lines.num_lines())
2087
2088     def test_collapse_strings(self):
2089         collapse = cpp_style.CleansedLines.collapse_strings
2090         self.assertEquals('""', collapse('""'))             # ""     (empty)
2091         self.assertEquals('"""', collapse('"""'))           # """    (bad)
2092         self.assertEquals('""', collapse('"xyz"'))          # "xyz"  (string)
2093         self.assertEquals('""', collapse('"\\\""'))         # "\""   (string)
2094         self.assertEquals('""', collapse('"\'"'))           # "'"    (string)
2095         self.assertEquals('"\"', collapse('"\"'))           # "\"    (bad)
2096         self.assertEquals('""', collapse('"\\\\"'))         # "\\"   (string)
2097         self.assertEquals('"', collapse('"\\\\\\"'))        # "\\\"  (bad)
2098         self.assertEquals('""', collapse('"\\\\\\\\"'))     # "\\\\" (string)
2099
2100         self.assertEquals('\'\'', collapse('\'\''))         # ''     (empty)
2101         self.assertEquals('\'\'', collapse('\'a\''))        # 'a'    (char)
2102         self.assertEquals('\'\'', collapse('\'\\\'\''))     # '\''   (char)
2103         self.assertEquals('\'', collapse('\'\\\''))         # '\'    (bad)
2104         self.assertEquals('', collapse('\\012'))            # '\012' (char)
2105         self.assertEquals('', collapse('\\xfF0'))           # '\xfF0' (char)
2106         self.assertEquals('', collapse('\\n'))              # '\n' (char)
2107         self.assertEquals('\#', collapse('\\#'))            # '\#' (bad)
2108
2109         self.assertEquals('StringReplace(body, "", "");',
2110                           collapse('StringReplace(body, "\\\\", "\\\\\\\\");'))
2111         self.assertEquals('\'\' ""',
2112                           collapse('\'"\' "foo"'))
2113
2114
2115 class OrderOfIncludesTest(CppStyleTestBase):
2116     def setUp(self):
2117         self.include_state = cpp_style._IncludeState()
2118
2119         # Cheat os.path.abspath called in FileInfo class.
2120         self.os_path_abspath_orig = os.path.abspath
2121         os.path.abspath = lambda value: value
2122
2123     def tearDown(self):
2124         os.path.abspath = self.os_path_abspath_orig
2125
2126     def test_try_drop_common_suffixes(self):
2127         self.assertEqual('foo/foo', cpp_style._drop_common_suffixes('foo/foo-inl.h'))
2128         self.assertEqual('foo/bar/foo',
2129                          cpp_style._drop_common_suffixes('foo/bar/foo_inl.h'))
2130         self.assertEqual('foo/foo', cpp_style._drop_common_suffixes('foo/foo.cpp'))
2131         self.assertEqual('foo/foo_unusualinternal',
2132                          cpp_style._drop_common_suffixes('foo/foo_unusualinternal.h'))
2133         self.assertEqual('',
2134                          cpp_style._drop_common_suffixes('_test.cpp'))
2135         self.assertEqual('test',
2136                          cpp_style._drop_common_suffixes('test.cpp'))
2137
2138
2139 class OrderOfIncludesTest(CppStyleTestBase):
2140     def setUp(self):
2141         self.include_state = cpp_style._IncludeState()
2142
2143         # Cheat os.path.abspath called in FileInfo class.
2144         self.os_path_abspath_orig = os.path.abspath
2145         os.path.abspath = lambda value: value
2146
2147     def tearDown(self):
2148         os.path.abspath = self.os_path_abspath_orig
2149
2150     def test_check_next_include_order__no_config(self):
2151         self.assertEqual('Header file should not contain WebCore config.h.',
2152                          self.include_state.check_next_include_order(cpp_style._CONFIG_HEADER, True))
2153
2154     def test_check_next_include_order__no_self(self):
2155         self.assertEqual('Header file should not contain itself.',
2156                          self.include_state.check_next_include_order(cpp_style._PRIMARY_HEADER, True))
2157         # Test actual code to make sure that header types are correctly assigned.
2158         self.assert_language_rules_check('Foo.h',
2159                                          '#include "Foo.h"\n',
2160                                          'Header file should not contain itself. Should be: alphabetically sorted.'
2161                                          '  [build/include_order] [4]')
2162         self.assert_language_rules_check('FooBar.h',
2163                                          '#include "Foo.h"\n',
2164                                          '')
2165
2166     def test_check_next_include_order__likely_then_config(self):
2167         self.assertEqual('Found header this file implements before WebCore config.h.',
2168                          self.include_state.check_next_include_order(cpp_style._PRIMARY_HEADER, False))
2169         self.assertEqual('Found WebCore config.h after a header this file implements.',
2170                          self.include_state.check_next_include_order(cpp_style._CONFIG_HEADER, False))
2171
2172     def test_check_next_include_order__other_then_config(self):
2173         self.assertEqual('Found other header before WebCore config.h.',
2174                          self.include_state.check_next_include_order(cpp_style._OTHER_HEADER, False))
2175         self.assertEqual('Found WebCore config.h after other header.',
2176                          self.include_state.check_next_include_order(cpp_style._CONFIG_HEADER, False))
2177
2178     def test_check_next_include_order__config_then_other_then_likely(self):
2179         self.assertEqual('', self.include_state.check_next_include_order(cpp_style._CONFIG_HEADER, False))
2180         self.assertEqual('Found other header before a header this file implements.',
2181                          self.include_state.check_next_include_order(cpp_style._OTHER_HEADER, False))
2182         self.assertEqual('Found header this file implements after other header.',
2183                          self.include_state.check_next_include_order(cpp_style._PRIMARY_HEADER, False))
2184
2185     def test_check_alphabetical_include_order(self):
2186         self.assert_language_rules_check('foo.h',
2187                                          '#include "a.h"\n'
2188                                          '#include "c.h"\n'
2189                                          '#include "b.h"\n',
2190                                          'Alphabetical sorting problem.  [build/include_order] [4]')
2191
2192         self.assert_language_rules_check('foo.h',
2193                                          '#include "a.h"\n'
2194                                          '#include "b.h"\n'
2195                                          '#include "c.h"\n',
2196                                          '')
2197
2198         self.assert_language_rules_check('foo.h',
2199                                          '#include <assert.h>\n'
2200                                          '#include "bar.h"\n',
2201                                          'Alphabetical sorting problem.  [build/include_order] [4]')
2202
2203         self.assert_language_rules_check('foo.h',
2204                                          '#include "bar.h"\n'
2205                                          '#include <assert.h>\n',
2206                                          '')
2207
2208     def test_check_line_break_after_own_header(self):
2209         self.assert_language_rules_check('foo.cpp',
2210                                          '#include "config.h"\n'
2211                                          '#include "foo.h"\n'
2212                                          '#include "bar.h"\n',
2213                                          'You should add a blank line after implementation file\'s own header.  [build/include_order] [4]')
2214
2215         self.assert_language_rules_check('foo.cpp',
2216                                          '#include "config.h"\n'
2217                                          '#include "foo.h"\n'
2218                                          '\n'
2219                                          '#include "bar.h"\n',
2220                                          '')
2221
2222     def test_check_preprocessor_in_include_section(self):
2223         self.assert_language_rules_check('foo.cpp',
2224                                          '#include "config.h"\n'
2225                                          '#include "foo.h"\n'
2226                                          '\n'
2227                                          '#ifdef BAZ\n'
2228                                          '#include "baz.h"\n'
2229                                          '#else\n'
2230                                          '#include "foobar.h"\n'
2231                                          '#endif"\n'
2232                                          '#include "bar.h"\n', # No flag because previous is in preprocessor section
2233                                          '')
2234
2235         self.assert_language_rules_check('foo.cpp',
2236                                          '#include "config.h"\n'
2237                                          '#include "foo.h"\n'
2238                                          '\n'
2239                                          '#ifdef BAZ\n'
2240                                          '#include "baz.h"\n'
2241                                          '#endif"\n'
2242                                          '#include "bar.h"\n'
2243                                          '#include "a.h"\n', # Should still flag this.
2244                                          'Alphabetical sorting problem.  [build/include_order] [4]')
2245
2246         self.assert_language_rules_check('foo.cpp',
2247                                          '#include "config.h"\n'
2248                                          '#include "foo.h"\n'
2249                                          '\n'
2250                                          '#ifdef BAZ\n'
2251                                          '#include "baz.h"\n'
2252                                          '#include "bar.h"\n' #Should still flag this
2253                                          '#endif"\n',
2254                                          'Alphabetical sorting problem.  [build/include_order] [4]')
2255
2256         self.assert_language_rules_check('foo.cpp',
2257                                          '#include "config.h"\n'
2258                                          '#include "foo.h"\n'
2259                                          '\n'
2260                                          '#ifdef BAZ\n'
2261                                          '#include "baz.h"\n'
2262                                          '#endif"\n'
2263                                          '#ifdef FOOBAR\n'
2264                                          '#include "foobar.h"\n'
2265                                          '#endif"\n'
2266                                          '#include "bar.h"\n'
2267                                          '#include "a.h"\n', # Should still flag this.
2268                                          'Alphabetical sorting problem.  [build/include_order] [4]')
2269
2270         # Check that after an already included error, the sorting rules still work.
2271         self.assert_language_rules_check('foo.cpp',
2272                                          '#include "config.h"\n'
2273                                          '#include "foo.h"\n'
2274                                          '\n'
2275                                          '#include "foo.h"\n'
2276                                          '#include "g.h"\n',
2277                                          '"foo.h" already included at foo.cpp:1  [build/include] [4]')
2278
2279     def test_check_wtf_includes(self):
2280         self.assert_language_rules_check('foo.cpp',
2281                                          '#include "config.h"\n'
2282                                          '#include "foo.h"\n'
2283                                          '\n'
2284                                          '#include <wtf/Assertions.h>\n',
2285                                          '')
2286         self.assert_language_rules_check('foo.cpp',
2287                                          '#include "config.h"\n'
2288                                          '#include "foo.h"\n'
2289                                          '\n'
2290                                          '#include "wtf/Assertions.h"\n',
2291                                          'wtf includes should be <wtf/file.h> instead of "wtf/file.h".'
2292                                          '  [build/include] [4]')
2293
2294     def test_classify_include(self):
2295         classify_include = cpp_style._classify_include
2296         include_state = cpp_style._IncludeState()
2297         self.assertEqual(cpp_style._CONFIG_HEADER,
2298                          classify_include('foo/foo.cpp',
2299                                           'config.h',
2300                                           False, include_state))
2301         self.assertEqual(cpp_style._PRIMARY_HEADER,
2302                          classify_include('foo/internal/foo.cpp',
2303                                           'foo/public/foo.h',
2304                                           False, include_state))
2305         self.assertEqual(cpp_style._PRIMARY_HEADER,
2306                          classify_include('foo/internal/foo.cpp',
2307                                           'foo/other/public/foo.h',
2308                                           False, include_state))
2309         self.assertEqual(cpp_style._OTHER_HEADER,
2310                          classify_include('foo/internal/foo.cpp',
2311                                           'foo/other/public/foop.h',
2312                                           False, include_state))
2313         self.assertEqual(cpp_style._OTHER_HEADER,
2314                          classify_include('foo/foo.cpp',
2315                                           'string',
2316                                           True, include_state))
2317         self.assertEqual(cpp_style._PRIMARY_HEADER,
2318                          classify_include('fooCustom.cpp',
2319                                           'foo.h',
2320                                           False, include_state))
2321         self.assertEqual(cpp_style._PRIMARY_HEADER,
2322                          classify_include('PrefixFooCustom.cpp',
2323                                           'Foo.h',
2324                                           False, include_state))
2325         # Tricky example where both includes might be classified as primary.
2326         self.assert_language_rules_check('ScrollbarThemeWince.cpp',
2327                                          '#include "config.h"\n'
2328                                          '#include "ScrollbarThemeWince.h"\n'
2329                                          '\n'
2330                                          '#include "Scrollbar.h"\n',
2331                                          '')
2332         self.assert_language_rules_check('ScrollbarThemeWince.cpp',
2333                                          '#include "config.h"\n'
2334                                          '#include "Scrollbar.h"\n'
2335                                          '\n'
2336                                          '#include "ScrollbarThemeWince.h"\n',
2337                                          'Found header this file implements after a header this file implements.'
2338                                          ' Should be: config.h, primary header, blank line, and then alphabetically sorted.'
2339                                          '  [build/include_order] [4]')
2340
2341     def test_try_drop_common_suffixes(self):
2342         self.assertEqual('foo/foo', cpp_style._drop_common_suffixes('foo/foo-inl.h'))
2343         self.assertEqual('foo/bar/foo',
2344                          cpp_style._drop_common_suffixes('foo/bar/foo_inl.h'))
2345         self.assertEqual('foo/foo', cpp_style._drop_common_suffixes('foo/foo.cpp'))
2346         self.assertEqual('foo/foo_unusualinternal',
2347                          cpp_style._drop_common_suffixes('foo/foo_unusualinternal.h'))
2348         self.assertEqual('',
2349                          cpp_style._drop_common_suffixes('_test.cpp'))
2350         self.assertEqual('test',
2351                          cpp_style._drop_common_suffixes('test.cpp'))
2352         self.assertEqual('test',
2353                          cpp_style._drop_common_suffixes('test.cpp'))
2354
2355 class CheckForFunctionLengthsTest(CppStyleTestBase):
2356     def setUp(self):
2357         # Reducing these thresholds for the tests speeds up tests significantly.
2358         self.old_normal_trigger = cpp_style._FunctionState._NORMAL_TRIGGER
2359         self.old_test_trigger = cpp_style._FunctionState._TEST_TRIGGER
2360
2361         cpp_style._FunctionState._NORMAL_TRIGGER = 10
2362         cpp_style._FunctionState._TEST_TRIGGER = 25
2363
2364     def tearDown(self):
2365         cpp_style._FunctionState._NORMAL_TRIGGER = self.old_normal_trigger
2366         cpp_style._FunctionState._TEST_TRIGGER = self.old_test_trigger
2367
2368     def assert_function_lengths_check(self, code, expected_message):
2369         """Check warnings for long function bodies are as expected.
2370
2371         Args:
2372           code: C++ source code expected to generate a warning message.
2373           expected_message: Message expected to be generated by the C++ code.
2374         """
2375         self.assertEquals(expected_message,
2376                           self.perform_function_lengths_check(code))
2377
2378     def trigger_lines(self, error_level):
2379         """Return number of lines needed to trigger a function length warning.
2380
2381         Args:
2382           error_level: --v setting for cpp_style.
2383
2384         Returns:
2385           Number of lines needed to trigger a function length warning.
2386         """
2387         return cpp_style._FunctionState._NORMAL_TRIGGER * 2 ** error_level
2388
2389     def trigger_test_lines(self, error_level):
2390         """Return number of lines needed to trigger a test function length warning.
2391
2392         Args:
2393           error_level: --v setting for cpp_style.
2394
2395         Returns:
2396           Number of lines needed to trigger a test function length warning.
2397         """
2398         return cpp_style._FunctionState._TEST_TRIGGER * 2 ** error_level
2399
2400     def assert_function_length_check_definition(self, lines, error_level):
2401         """Generate long function definition and check warnings are as expected.
2402
2403         Args:
2404           lines: Number of lines to generate.
2405           error_level:  --v setting for cpp_style.
2406         """
2407         trigger_level = self.trigger_lines(cpp_style._verbose_level())
2408         self.assert_function_lengths_check(
2409             'void test(int x)' + self.function_body(lines),
2410             ('Small and focused functions are preferred: '
2411              'test() has %d non-comment lines '
2412              '(error triggered by exceeding %d lines).'
2413              '  [readability/fn_size] [%d]'
2414              % (lines, trigger_level, error_level)))
2415
2416     def assert_function_length_check_definition_ok(self, lines):
2417         """Generate shorter function definition and check no warning is produced.
2418
2419         Args:
2420           lines: Number of lines to generate.
2421         """
2422         self.assert_function_lengths_check(
2423             'void test(int x)' + self.function_body(lines),
2424             '')
2425
2426     def assert_function_length_check_at_error_level(self, error_level):
2427         """Generate and check function at the trigger level for --v setting.
2428
2429         Args:
2430           error_level: --v setting for cpp_style.
2431         """
2432         self.assert_function_length_check_definition(self.trigger_lines(error_level),
2433                                                      error_level)
2434
2435     def assert_function_length_check_below_error_level(self, error_level):
2436         """Generate and check function just below the trigger level for --v setting.
2437
2438         Args:
2439           error_level: --v setting for cpp_style.
2440         """
2441         self.assert_function_length_check_definition(self.trigger_lines(error_level) - 1,
2442                                                      error_level - 1)
2443
2444     def assert_function_length_check_above_error_level(self, error_level):
2445         """Generate and check function just above the trigger level for --v setting.
2446
2447         Args:
2448           error_level: --v setting for cpp_style.
2449         """
2450         self.assert_function_length_check_definition(self.trigger_lines(error_level) + 1,
2451                                                      error_level)
2452
2453     def function_body(self, number_of_lines):
2454         return ' {\n' + '    this_is_just_a_test();\n' * number_of_lines + '}'
2455
2456     def function_body_with_blank_lines(self, number_of_lines):
2457         return ' {\n' + '    this_is_just_a_test();\n\n' * number_of_lines + '}'
2458
2459     def function_body_with_no_lints(self, number_of_lines):
2460         return ' {\n' + '    this_is_just_a_test();  // NOLINT\n' * number_of_lines + '}'
2461
2462     # Test line length checks.
2463     def test_function_length_check_declaration(self):
2464         self.assert_function_lengths_check(
2465             'void test();',  # Not a function definition
2466             '')
2467
2468     def test_function_length_check_declaration_with_block_following(self):
2469         self.assert_function_lengths_check(
2470             ('void test();\n'
2471              + self.function_body(66)),  # Not a function definition
2472             '')
2473
2474     def test_function_length_check_class_definition(self):
2475         self.assert_function_lengths_check(  # Not a function definition
2476             'class Test' + self.function_body(66) + ';',
2477             '')
2478
2479     def test_function_length_check_trivial(self):
2480         self.assert_function_lengths_check(
2481             'void test() {}',  # Not counted
2482             '')
2483
2484     def test_function_length_check_empty(self):
2485         self.assert_function_lengths_check(
2486             'void test() {\n}',
2487             '')
2488
2489     def test_function_length_check_definition_below_severity0(self):
2490         old_verbosity = cpp_style._set_verbose_level(0)
2491         self.assert_function_length_check_definition_ok(self.trigger_lines(0) - 1)
2492         cpp_style._set_verbose_level(old_verbosity)
2493
2494     def test_function_length_check_definition_at_severity0(self):
2495         old_verbosity = cpp_style._set_verbose_level(0)
2496         self.assert_function_length_check_definition_ok(self.trigger_lines(0))
2497         cpp_style._set_verbose_level(old_verbosity)
2498
2499     def test_function_length_check_definition_above_severity0(self):
2500         old_verbosity = cpp_style._set_verbose_level(0)
2501         self.assert_function_length_check_above_error_level(0)
2502         cpp_style._set_verbose_level(old_verbosity)
2503
2504     def test_function_length_check_definition_below_severity1v0(self):
2505         old_verbosity = cpp_style._set_verbose_level(0)
2506         self.assert_function_length_check_below_error_level(1)
2507         cpp_style._set_verbose_level(old_verbosity)
2508
2509     def test_function_length_check_definition_at_severity1v0(self):
2510         old_verbosity = cpp_style._set_verbose_level(0)
2511         self.assert_function_length_check_at_error_level(1)
2512         cpp_style._set_verbose_level(old_verbosity)
2513
2514     def test_function_length_check_definition_below_severity1(self):
2515         self.assert_function_length_check_definition_ok(self.trigger_lines(1) - 1)
2516
2517     def test_function_length_check_definition_at_severity1(self):
2518         self.assert_function_length_check_definition_ok(self.trigger_lines(1))
2519
2520     def test_function_length_check_definition_above_severity1(self):
2521         self.assert_function_length_check_above_error_level(1)
2522
2523     def test_function_length_check_definition_severity1_plus_blanks(self):
2524         error_level = 1
2525         error_lines = self.trigger_lines(error_level) + 1
2526         trigger_level = self.trigger_lines(cpp_style._verbose_level())
2527         self.assert_function_lengths_check(
2528             'void test_blanks(int x)' + self.function_body(error_lines),
2529             ('Small and focused functions are preferred: '
2530              'test_blanks() has %d non-comment lines '
2531              '(error triggered by exceeding %d lines).'
2532              '  [readability/fn_size] [%d]')
2533             % (error_lines, trigger_level, error_level))
2534
2535     def test_function_length_check_complex_definition_severity1(self):
2536         error_level = 1
2537         error_lines = self.trigger_lines(error_level) + 1
2538         trigger_level = self.trigger_lines(cpp_style._verbose_level())
2539         self.assert_function_lengths_check(
2540             ('my_namespace::my_other_namespace::MyVeryLongTypeName*\n'
2541              'my_namespace::my_other_namespace::MyFunction(int arg1, char* arg2)'
2542              + self.function_body(error_lines)),
2543             ('Small and focused functions are preferred: '
2544              'my_namespace::my_other_namespace::MyFunction()'
2545              ' has %d non-comment lines '
2546              '(error triggered by exceeding %d lines).'
2547              '  [readability/fn_size] [%d]')
2548             % (error_lines, trigger_level, error_level))
2549
2550     def test_function_length_check_definition_severity1_for_test(self):
2551         error_level = 1
2552         error_lines = self.trigger_test_lines(error_level) + 1
2553         trigger_level = self.trigger_test_lines(cpp_style._verbose_level())
2554         self.assert_function_lengths_check(
2555             'TEST_F(Test, Mutator)' + self.function_body(error_lines),
2556             ('Small and focused functions are preferred: '
2557              'TEST_F(Test, Mutator) has %d non-comment lines '
2558              '(error triggered by exceeding %d lines).'
2559              '  [readability/fn_size] [%d]')
2560             % (error_lines, trigger_level, error_level))
2561
2562     def test_function_length_check_definition_severity1_for_split_line_test(self):
2563         error_level = 1
2564         error_lines = self.trigger_test_lines(error_level) + 1
2565         trigger_level = self.trigger_test_lines(cpp_style._verbose_level())
2566         self.assert_function_lengths_check(
2567             ('TEST_F(GoogleUpdateRecoveryRegistryProtectedTest,\n'
2568              '    FixGoogleUpdate_AllValues_MachineApp)'  # note: 4 spaces
2569              + self.function_body(error_lines)),
2570             ('Small and focused functions are preferred: '
2571              'TEST_F(GoogleUpdateRecoveryRegistryProtectedTest, '  # 1 space
2572              'FixGoogleUpdate_AllValues_MachineApp) has %d non-comment lines '
2573              '(error triggered by exceeding %d lines).'
2574              '  [readability/fn_size] [%d]')
2575             % (error_lines+1, trigger_level, error_level))
2576
2577     def test_function_length_check_definition_severity1_for_bad_test_doesnt_break(self):
2578         error_level = 1
2579         error_lines = self.trigger_test_lines(error_level) + 1
2580         trigger_level = self.trigger_test_lines(cpp_style._verbose_level())
2581         self.assert_function_lengths_check(
2582             ('TEST_F('
2583              + self.function_body(error_lines)),
2584             ('Small and focused functions are preferred: '
2585              'TEST_F has %d non-comment lines '
2586              '(error triggered by exceeding %d lines).'
2587              '  [readability/fn_size] [%d]')
2588             % (error_lines, trigger_level, error_level))
2589
2590     def test_function_length_check_definition_severity1_with_embedded_no_lints(self):
2591         error_level = 1
2592         error_lines = self.trigger_lines(error_level) + 1
2593         trigger_level = self.trigger_lines(cpp_style._verbose_level())
2594         self.assert_function_lengths_check(
2595             'void test(int x)' + self.function_body_with_no_lints(error_lines),
2596             ('Small and focused functions are preferred: '
2597              'test() has %d non-comment lines '
2598              '(error triggered by exceeding %d lines).'
2599              '  [readability/fn_size] [%d]')
2600             % (error_lines, trigger_level, error_level))
2601
2602     def test_function_length_check_definition_severity1_with_no_lint(self):
2603         self.assert_function_lengths_check(
2604             ('void test(int x)' + self.function_body(self.trigger_lines(1))
2605              + '  // NOLINT -- long function'),
2606             '')
2607
2608     def test_function_length_check_definition_below_severity2(self):
2609         self.assert_function_length_check_below_error_level(2)
2610
2611     def test_function_length_check_definition_severity2(self):
2612         self.assert_function_length_check_at_error_level(2)
2613
2614     def test_function_length_check_definition_above_severity2(self):
2615         self.assert_function_length_check_above_error_level(2)
2616
2617     def test_function_length_check_definition_below_severity3(self):
2618         self.assert_function_length_check_below_error_level(3)
2619
2620     def test_function_length_check_definition_severity3(self):
2621         self.assert_function_length_check_at_error_level(3)
2622
2623     def test_function_length_check_definition_above_severity3(self):
2624         self.assert_function_length_check_above_error_level(3)
2625
2626     def test_function_length_check_definition_below_severity4(self):
2627         self.assert_function_length_check_below_error_level(4)
2628
2629     def test_function_length_check_definition_severity4(self):
2630         self.assert_function_length_check_at_error_level(4)
2631
2632     def test_function_length_check_definition_above_severity4(self):
2633         self.assert_function_length_check_above_error_level(4)
2634
2635     def test_function_length_check_definition_below_severity5(self):
2636         self.assert_function_length_check_below_error_level(5)
2637
2638     def test_function_length_check_definition_at_severity5(self):
2639         self.assert_function_length_check_at_error_level(5)
2640
2641     def test_function_length_check_definition_above_severity5(self):
2642         self.assert_function_length_check_above_error_level(5)
2643
2644     def test_function_length_check_definition_huge_lines(self):
2645         # 5 is the limit
2646         self.assert_function_length_check_definition(self.trigger_lines(10), 5)
2647
2648     def test_function_length_not_determinable(self):
2649         # Macro invocation without terminating semicolon.
2650         self.assert_function_lengths_check(
2651             'MACRO(arg)',
2652             '')
2653
2654         # Macro with underscores
2655         self.assert_function_lengths_check(
2656             'MACRO_WITH_UNDERSCORES(arg1, arg2, arg3)',
2657             '')
2658
2659         self.assert_function_lengths_check(
2660             'NonMacro(arg)',
2661             'Lint failed to find start of function body.'
2662             '  [readability/fn_size] [5]')
2663
2664
2665 class NoNonVirtualDestructorsTest(CppStyleTestBase):
2666
2667     def test_no_error(self):
2668         self.assert_multi_line_lint(
2669             '''class Foo {
2670                    virtual ~Foo();
2671                    virtual void foo();
2672                };''',
2673             '')
2674
2675         self.assert_multi_line_lint(
2676             '''class Foo {
2677                    virtual inline ~Foo();
2678                    virtual void foo();
2679                };''',
2680             '')
2681
2682         self.assert_multi_line_lint(
2683             '''class Foo {
2684                    inline virtual ~Foo();
2685                    virtual void foo();
2686                };''',
2687             '')
2688
2689         self.assert_multi_line_lint(
2690             '''class Foo::Goo {
2691                    virtual ~Goo();
2692                    virtual void goo();
2693                };''',
2694             '')
2695         self.assert_multi_line_lint(
2696             'class Foo { void foo(); };',
2697             'More than one command on the same line  [whitespace/newline] [4]')
2698
2699         self.assert_multi_line_lint(
2700             '''class Qualified::Goo : public Foo {
2701                    virtual void goo();
2702                };''',
2703             '')
2704
2705         self.assert_multi_line_lint(
2706             # Line-ending :
2707             '''class Goo :
2708                public Foo {
2709                     virtual void goo();
2710                };''',
2711             'Labels should always be indented at least one space.  If this is a '
2712             'member-initializer list in a constructor, the colon should be on the '
2713             'line after the definition header.  [whitespace/labels] [4]')
2714
2715     def test_no_destructor_when_virtual_needed(self):
2716         self.assert_multi_line_lint_re(
2717             '''class Foo {
2718                    virtual void foo();
2719                };''',
2720             'The class Foo probably needs a virtual destructor')
2721
2722     def test_destructor_non_virtual_when_virtual_needed(self):
2723         self.assert_multi_line_lint_re(
2724             '''class Foo {
2725                    ~Foo();
2726                    virtual void foo();
2727                };''',
2728             'The class Foo probably needs a virtual destructor')
2729
2730     def test_no_warn_when_derived(self):
2731         self.assert_multi_line_lint(
2732             '''class Foo : public Goo {
2733                    virtual void foo();
2734                };''',
2735             '')
2736
2737     def test_internal_braces(self):
2738         self.assert_multi_line_lint_re(
2739             '''class Foo {
2740                    enum Goo {
2741                        GOO
2742                    };
2743                    virtual void foo();
2744                };''',
2745             'The class Foo probably needs a virtual destructor')
2746
2747     def test_inner_class_needs_virtual_destructor(self):
2748         self.assert_multi_line_lint_re(
2749             '''class Foo {
2750                    class Goo {
2751                        virtual void goo();
2752                    };
2753                };''',
2754             'The class Goo probably needs a virtual destructor')
2755
2756     def test_outer_class_needs_virtual_destructor(self):
2757         self.assert_multi_line_lint_re(
2758             '''class Foo {
2759                    class Goo {
2760                    };
2761                    virtual void foo();
2762                };''',
2763             'The class Foo probably needs a virtual destructor')
2764
2765     def test_qualified_class_needs_virtual_destructor(self):
2766         self.assert_multi_line_lint_re(
2767             '''class Qualified::Foo {
2768                    virtual void foo();
2769                };''',
2770             'The class Qualified::Foo probably needs a virtual destructor')
2771
2772     def test_multi_line_declaration_no_error(self):
2773         self.assert_multi_line_lint_re(
2774             '''class Foo
2775                    : public Goo {
2776                    virtual void foo();
2777                };''',
2778             '')
2779
2780     def test_multi_line_declaration_with_error(self):
2781         self.assert_multi_line_lint(
2782             '''class Foo
2783                {
2784                    virtual void foo();
2785                };''',
2786             ['This { should be at the end of the previous line  '
2787              '[whitespace/braces] [4]',
2788              'The class Foo probably needs a virtual destructor due to having '
2789              'virtual method(s), one declared at line 2.  [runtime/virtual] [4]'])
2790
2791
2792 class CppStyleStateTest(unittest.TestCase):
2793     def test_error_count(self):
2794         self.assertEquals(0, cpp_style.error_count())
2795         cpp_style._cpp_style_state.increment_error_count()
2796         cpp_style._cpp_style_state.increment_error_count()
2797         self.assertEquals(2, cpp_style.error_count())
2798         cpp_style._cpp_style_state.reset_error_count()
2799         self.assertEquals(0, cpp_style.error_count())
2800
2801
2802 class WebKitStyleTest(CppStyleTestBase):
2803
2804     # for http://webkit.org/coding/coding-style.html
2805     def test_indentation(self):
2806         # 1. Use spaces, not tabs. Tabs should only appear in files that
2807         #    require them for semantic meaning, like Makefiles.
2808         self.assert_multi_line_lint(
2809             'class Foo {\n'
2810             '    int goo;\n'
2811             '};',
2812             '')
2813         self.assert_multi_line_lint(
2814             'class Foo {\n'
2815             '\tint goo;\n'
2816             '};',
2817             'Tab found; better to use spaces  [whitespace/tab] [1]')
2818
2819         # 2. The indent size is 4 spaces.
2820         self.assert_multi_line_lint(
2821             'class Foo {\n'
2822             '    int goo;\n'
2823             '};',
2824             '')
2825         self.assert_multi_line_lint(
2826             'class Foo {\n'
2827             '   int goo;\n'
2828             '};',
2829             'Weird number of spaces at line-start.  Are you using a 4-space indent?  [whitespace/indent] [3]')
2830         # FIXME: No tests for 8-spaces.
2831
2832         # 3. In a header, code inside a namespace should not be indented.
2833         self.assert_multi_line_lint(
2834             'namespace WebCore {\n\n'
2835             'class Document {\n'
2836             '    int myVariable;\n'
2837             '};\n'
2838             '}',
2839             '',
2840             'foo.h')
2841         self.assert_multi_line_lint(
2842             'namespace OuterNamespace {\n'
2843             '    namespace InnerNamespace {\n'
2844             '    class Document {\n'
2845             '};\n'
2846             '};\n'
2847             '}',
2848             'Code inside a namespace should not be indented.  [whitespace/indent] [4]',
2849             'foo.h')
2850         self.assert_multi_line_lint(
2851             'namespace OuterNamespace {\n'
2852             '    class Document {\n'
2853             '    namespace InnerNamespace {\n'
2854             '};\n'
2855             '};\n'
2856             '}',
2857             'Code inside a namespace should not be indented.  [whitespace/indent] [4]',
2858             'foo.h')
2859         self.assert_multi_line_lint(
2860             'namespace WebCore {\n'
2861             '#if 0\n'
2862             '    class Document {\n'
2863             '};\n'
2864             '#endif\n'
2865             '}',
2866             'Code inside a namespace should not be indented.  [whitespace/indent] [4]',
2867             'foo.h')
2868         self.assert_multi_line_lint(
2869             'namespace WebCore {\n'
2870             'class Document {\n'
2871             '};\n'
2872             '}',
2873             '',
2874             'foo.h')
2875
2876         # 4. In an implementation file (files with the extension .cpp, .c
2877         #    or .mm), code inside a namespace should not be indented.
2878         self.assert_multi_line_lint(
2879             'namespace WebCore {\n\n'
2880             'Document::Foo()\n'
2881             '    : foo(bar)\n'
2882             '    , boo(far)\n'
2883             '{\n'
2884             '    stuff();\n'
2885             '}',
2886             '',
2887             'foo.cpp')
2888         self.assert_multi_line_lint(
2889             'namespace OuterNamespace {\n'
2890             'namespace InnerNamespace {\n'
2891             'Document::Foo() { }\n'
2892             '    void* p;\n'
2893             '}\n'
2894             '}\n',
2895             'Code inside a namespace should not be indented.  [whitespace/indent] [4]',
2896             'foo.cpp')
2897         self.assert_multi_line_lint(
2898             'namespace OuterNamespace {\n'
2899             'namespace InnerNamespace {\n'
2900             'Document::Foo() { }\n'
2901             '}\n'
2902             '    void* p;\n'
2903             '}\n',
2