OLD | NEW |
1 #!/usr/bin/python2.4 | 1 #!/usr/bin/python2.4 |
2 # -*- coding: utf-8; -*- | 2 # -*- coding: utf-8; -*- |
3 # | 3 # |
4 # Copyright (c) 2009 Google Inc. All rights reserved. | 4 # Copyright (c) 2009 Google Inc. All rights reserved. |
5 # | 5 # |
6 # Redistribution and use in source and binary forms, with or without | 6 # Redistribution and use in source and binary forms, with or without |
7 # modification, are permitted provided that the following conditions are | 7 # modification, are permitted provided that the following conditions are |
8 # met: | 8 # met: |
9 # | 9 # |
10 # * Redistributions of source code must retain the above copyright | 10 # * Redistributions of source code must retain the above copyright |
(...skipping 28 matching lines...) Expand all Loading... |
39 import re | 39 import re |
40 import unittest | 40 import unittest |
41 import cpplint | 41 import cpplint |
42 | 42 |
43 | 43 |
44 # This class works as an error collector and replaces cpplint.Error | 44 # This class works as an error collector and replaces cpplint.Error |
45 # function for the unit tests. We also verify each category we see | 45 # function for the unit tests. We also verify each category we see |
46 # is in cpplint._ERROR_CATEGORIES, to help keep that list up to date. | 46 # is in cpplint._ERROR_CATEGORIES, to help keep that list up to date. |
47 class ErrorCollector: | 47 class ErrorCollector: |
48 # These are a global list, covering all categories seen ever. | 48 # These are a global list, covering all categories seen ever. |
49 _ERROR_CATEGORIES = [x.strip() # get rid of leading whitespace | 49 _ERROR_CATEGORIES = cpplint._ERROR_CATEGORIES |
50 for x in cpplint._ERROR_CATEGORIES.split()] | |
51 _SEEN_ERROR_CATEGORIES = {} | 50 _SEEN_ERROR_CATEGORIES = {} |
52 | 51 |
53 def __init__(self, assert_fn): | 52 def __init__(self, assert_fn): |
54 """assert_fn: a function to call when we notice a problem.""" | 53 """assert_fn: a function to call when we notice a problem.""" |
55 self._assert_fn = assert_fn | 54 self._assert_fn = assert_fn |
56 self._errors = [] | 55 self._errors = [] |
| 56 cpplint.ResetNolintSuppressions() |
57 | 57 |
58 def __call__(self, unused_filename, unused_linenum, | 58 def __call__(self, unused_filename, linenum, |
59 category, confidence, message): | 59 category, confidence, message): |
60 self._assert_fn(category in self._ERROR_CATEGORIES, | 60 self._assert_fn(category in self._ERROR_CATEGORIES, |
61 'Message "%s" has category "%s",' | 61 'Message "%s" has category "%s",' |
62 ' which is not in _ERROR_CATEGORIES' % (message, category)) | 62 ' which is not in _ERROR_CATEGORIES' % (message, category)) |
63 self._SEEN_ERROR_CATEGORIES[category] = 1 | 63 self._SEEN_ERROR_CATEGORIES[category] = 1 |
64 if cpplint._ShouldPrintError(category, confidence): | 64 if cpplint._ShouldPrintError(category, confidence, linenum): |
65 self._errors.append('%s [%s] [%d]' % (message, category, confidence)) | 65 self._errors.append('%s [%s] [%d]' % (message, category, confidence)) |
66 | 66 |
67 def Results(self): | 67 def Results(self): |
68 if len(self._errors) < 2: | 68 if len(self._errors) < 2: |
69 return ''.join(self._errors) # Most tests expect to have a string. | 69 return ''.join(self._errors) # Most tests expect to have a string. |
70 else: | 70 else: |
71 return self._errors # Let's give a list if there is more than one. | 71 return self._errors # Let's give a list if there is more than one. |
72 | 72 |
73 def ResultList(self): | 73 def ResultList(self): |
74 return self._errors | 74 return self._errors |
(...skipping 213 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
288 '// https://g' + ('o' * 100) + 'gle.com/', | 288 '// https://g' + ('o' * 100) + 'gle.com/', |
289 '') | 289 '') |
290 self.TestLint( | 290 self.TestLint( |
291 '// https://g' + ('o' * 60) + 'gle.com/ and some comments', | 291 '// https://g' + ('o' * 60) + 'gle.com/ and some comments', |
292 'Lines should be <= 80 characters long' | 292 'Lines should be <= 80 characters long' |
293 ' [whitespace/line_length] [2]') | 293 ' [whitespace/line_length] [2]') |
294 self.TestLint( | 294 self.TestLint( |
295 '// Read https://g' + ('o' * 60) + 'gle.com/' , | 295 '// Read https://g' + ('o' * 60) + 'gle.com/' , |
296 '') | 296 '') |
297 | 297 |
| 298 # Test error suppression annotations. |
| 299 def testErrorSuppression(self): |
| 300 # Two errors on same line: |
| 301 self.TestLint( |
| 302 'long a = (int64) 65;', |
| 303 ['Using C-style cast. Use static_cast<int64>(...) instead' |
| 304 ' [readability/casting] [4]', |
| 305 'Use int16/int64/etc, rather than the C type long' |
| 306 ' [runtime/int] [4]', |
| 307 ]) |
| 308 # One category of error suppressed: |
| 309 self.TestLint( |
| 310 'long a = (int64) 65; // NOLINT(runtime/int)', |
| 311 'Using C-style cast. Use static_cast<int64>(...) instead' |
| 312 ' [readability/casting] [4]') |
| 313 # All categories suppressed: (two aliases) |
| 314 self.TestLint('long a = (int64) 65; // NOLINT', '') |
| 315 self.TestLint('long a = (int64) 65; // NOLINT(*)', '') |
| 316 # Malformed NOLINT directive: |
| 317 self.TestLint( |
| 318 'long a = 65; // NOLINT(foo)', |
| 319 ['Unknown NOLINT error category: foo' |
| 320 ' [readability/nolint] [5]', |
| 321 'Use int16/int64/etc, rather than the C type long [runtime/int] [4]', |
| 322 ]) |
| 323 # Irrelevant NOLINT directive has no effect: |
| 324 self.TestLint( |
| 325 'long a = 65; // NOLINT(readability/casting)', |
| 326 'Use int16/int64/etc, rather than the C type long' |
| 327 ' [runtime/int] [4]') |
| 328 |
| 329 |
298 # Test Variable Declarations. | 330 # Test Variable Declarations. |
299 def testVariableDeclarations(self): | 331 def testVariableDeclarations(self): |
300 self.TestLint( | 332 self.TestLint( |
301 'long a = 65;', | 333 'long a = 65;', |
302 'Use int16/int64/etc, rather than the C type long' | 334 'Use int16/int64/etc, rather than the C type long' |
303 ' [runtime/int] [4]') | 335 ' [runtime/int] [4]') |
304 self.TestLint( | 336 self.TestLint( |
305 'long double b = 65.0;', | 337 'long double b = 65.0;', |
306 '') | 338 '') |
307 self.TestLint( | 339 self.TestLint( |
(...skipping 263 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
571 ' [build/include_what_you_use] [4]') | 603 ' [build/include_what_you_use] [4]') |
572 self.TestIncludeWhatYouUse( | 604 self.TestIncludeWhatYouUse( |
573 '''#include "base/foobar.h" | 605 '''#include "base/foobar.h" |
574 bool foobar = min<int>(0,1); | 606 bool foobar = min<int>(0,1); |
575 ''', | 607 ''', |
576 'Add #include <algorithm> for min [build/include_what_you_use] [4]') | 608 'Add #include <algorithm> for min [build/include_what_you_use] [4]') |
577 self.TestIncludeWhatYouUse( | 609 self.TestIncludeWhatYouUse( |
578 'void a(const string &foobar);', | 610 'void a(const string &foobar);', |
579 'Add #include <string> for string [build/include_what_you_use] [4]') | 611 'Add #include <string> for string [build/include_what_you_use] [4]') |
580 self.TestIncludeWhatYouUse( | 612 self.TestIncludeWhatYouUse( |
| 613 'void a(const std::string &foobar);', |
| 614 'Add #include <string> for string [build/include_what_you_use] [4]') |
| 615 self.TestIncludeWhatYouUse( |
| 616 'void a(const my::string &foobar);', |
| 617 '') # Avoid false positives on strings in other namespaces. |
| 618 self.TestIncludeWhatYouUse( |
581 '''#include "base/foobar.h" | 619 '''#include "base/foobar.h" |
582 bool foobar = swap(0,1); | 620 bool foobar = swap(0,1); |
583 ''', | 621 ''', |
584 'Add #include <algorithm> for swap [build/include_what_you_use] [4]') | 622 'Add #include <algorithm> for swap [build/include_what_you_use] [4]') |
585 self.TestIncludeWhatYouUse( | 623 self.TestIncludeWhatYouUse( |
586 '''#include "base/foobar.h" | 624 '''#include "base/foobar.h" |
587 bool foobar = transform(a.begin(), a.end(), b.start(), Foo); | 625 bool foobar = transform(a.begin(), a.end(), b.start(), Foo); |
588 ''', | 626 ''', |
589 'Add #include <algorithm> for transform ' | 627 'Add #include <algorithm> for transform ' |
590 '[build/include_what_you_use] [4]') | 628 '[build/include_what_you_use] [4]') |
(...skipping 1029 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1620 self.TestLint(' char* one_space_indent = "public:";', | 1658 self.TestLint(' char* one_space_indent = "public:";', |
1621 'Weird number of spaces at line-start. ' | 1659 'Weird number of spaces at line-start. ' |
1622 'Are you using a 2-space indent? [whitespace/indent] [3]') | 1660 'Are you using a 2-space indent? [whitespace/indent] [3]') |
1623 self.TestLint(' public:', '') | 1661 self.TestLint(' public:', '') |
1624 self.TestLint(' public:', '') | 1662 self.TestLint(' public:', '') |
1625 self.TestLint(' public:', '') | 1663 self.TestLint(' public:', '') |
1626 | 1664 |
1627 def testLabel(self): | 1665 def testLabel(self): |
1628 self.TestLint('public:', | 1666 self.TestLint('public:', |
1629 'Labels should always be indented at least one space. ' | 1667 'Labels should always be indented at least one space. ' |
1630 'If this is a member-initializer list in a constructor, ' | 1668 'If this is a member-initializer list in a constructor or ' |
1631 'the colon should be on the line after the definition ' | 1669 'the base class list in a class definition, the colon should ' |
1632 'header. [whitespace/labels] [4]') | 1670 'be on the following line. [whitespace/labels] [4]') |
1633 self.TestLint(' public:', '') | 1671 self.TestLint(' public:', '') |
1634 self.TestLint(' public:', '') | 1672 self.TestLint(' public:', '') |
1635 self.TestLint(' public:', '') | 1673 self.TestLint(' public:', '') |
1636 self.TestLint(' public:', '') | 1674 self.TestLint(' public:', '') |
1637 self.TestLint(' public:', '') | 1675 self.TestLint(' public:', '') |
1638 | 1676 |
1639 def testNotALabel(self): | 1677 def testNotALabel(self): |
1640 self.TestLint('MyVeryLongNamespace::MyVeryLongClassName::', '') | 1678 self.TestLint('MyVeryLongNamespace::MyVeryLongClassName::', '') |
1641 | 1679 |
1642 def testTab(self): | 1680 def testTab(self): |
(...skipping 324 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1967 '#ifndef header guard has wrong style, please use: %s' | 2005 '#ifndef header guard has wrong style, please use: %s' |
1968 ' [build/header_guard] [5]' % expected_guard), | 2006 ' [build/header_guard] [5]' % expected_guard), |
1969 error_collector.ResultList()) | 2007 error_collector.ResultList()) |
1970 self.assertEquals( | 2008 self.assertEquals( |
1971 0, | 2009 0, |
1972 error_collector.ResultList().count( | 2010 error_collector.ResultList().count( |
1973 '#endif line should be "#endif // %s"' | 2011 '#endif line should be "#endif // %s"' |
1974 ' [build/header_guard] [5]' % expected_guard), | 2012 ' [build/header_guard] [5]' % expected_guard), |
1975 error_collector.ResultList()) | 2013 error_collector.ResultList()) |
1976 | 2014 |
| 2015 # Special case for flymake |
| 2016 error_collector = ErrorCollector(self.assert_) |
| 2017 cpplint.ProcessFileData('mydir/foo_flymake.h', |
| 2018 'h', [], error_collector) |
| 2019 self.assertEquals( |
| 2020 1, |
| 2021 error_collector.ResultList().count( |
| 2022 'No #ifndef header guard found, suggested CPP variable is: %s' |
| 2023 ' [build/header_guard] [5]' % expected_guard), |
| 2024 error_collector.ResultList()) |
1977 | 2025 |
1978 def testBuildInclude(self): | 2026 def testBuildInclude(self): |
1979 # Test that include statements have slashes in them. | 2027 # Test that include statements have slashes in them. |
1980 self.TestLint('#include "foo.h"', | 2028 self.TestLint('#include "foo.h"', |
1981 'Include the directory when naming .h files' | 2029 'Include the directory when naming .h files' |
1982 ' [build/include] [4]') | 2030 ' [build/include] [4]') |
1983 | 2031 |
1984 def testBuildPrintfFormat(self): | 2032 def testBuildPrintfFormat(self): |
1985 self.TestLint( | 2033 self.TestLint( |
1986 r'printf("\%%d", value);', | 2034 r'printf("\%%d", value);', |
(...skipping 734 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2721 virtual void goo(); | 2769 virtual void goo(); |
2722 };''', | 2770 };''', |
2723 '') | 2771 '') |
2724 | 2772 |
2725 self.TestMultiLineLint( | 2773 self.TestMultiLineLint( |
2726 # Line-ending : | 2774 # Line-ending : |
2727 '''class Goo : | 2775 '''class Goo : |
2728 public Foo { | 2776 public Foo { |
2729 virtual void goo(); | 2777 virtual void goo(); |
2730 };''', | 2778 };''', |
2731 'Labels should always be indented at least one space. If this is a ' | 2779 'Labels should always be indented at least one space. ' |
2732 'member-initializer list in a constructor, the colon should be on the ' | 2780 'If this is a member-initializer list in a constructor or ' |
2733 'line after the definition header. [whitespace/labels] [4]') | 2781 'the base class list in a class definition, the colon should ' |
| 2782 'be on the following line. [whitespace/labels] [4]') |
2734 | 2783 |
2735 def testNoDestructorWhenVirtualNeeded(self): | 2784 def testNoDestructorWhenVirtualNeeded(self): |
2736 self.TestMultiLineLintRE( | 2785 self.TestMultiLineLintRE( |
2737 '''class Foo { | 2786 '''class Foo { |
2738 virtual void foo(); | 2787 virtual void foo(); |
2739 };''', | 2788 };''', |
2740 'The class Foo probably needs a virtual destructor') | 2789 'The class Foo probably needs a virtual destructor') |
2741 | 2790 |
2742 def testDestructorNonVirtualWhenVirtualNeeded(self): | 2791 def testDestructorNonVirtualWhenVirtualNeeded(self): |
2743 self.TestMultiLineLintRE( | 2792 self.TestMultiLineLintRE( |
(...skipping 57 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2801 self.TestMultiLineLint( | 2850 self.TestMultiLineLint( |
2802 '''class Foo | 2851 '''class Foo |
2803 { | 2852 { |
2804 virtual void foo(); | 2853 virtual void foo(); |
2805 };''', | 2854 };''', |
2806 ['{ should almost always be at the end of the previous line ' | 2855 ['{ should almost always be at the end of the previous line ' |
2807 '[whitespace/braces] [4]', | 2856 '[whitespace/braces] [4]', |
2808 'The class Foo probably needs a virtual destructor due to having ' | 2857 'The class Foo probably needs a virtual destructor due to having ' |
2809 'virtual method(s), one declared at line 2. [runtime/virtual] [4]']) | 2858 'virtual method(s), one declared at line 2. [runtime/virtual] [4]']) |
2810 | 2859 |
| 2860 def testSnprintfSize(self): |
| 2861 self.TestLint('vsnprintf(NULL, 0, format)', '') |
| 2862 self.TestLint('snprintf(fisk, 1, format)', |
| 2863 'If you can, use sizeof(fisk) instead of 1 as the 2nd arg ' |
| 2864 'to snprintf. [runtime/printf] [3]') |
| 2865 |
| 2866 |
2811 # pylint: disable-msg=C6409 | 2867 # pylint: disable-msg=C6409 |
2812 def setUp(): | 2868 def setUp(): |
2813 """ Runs before all tests are executed. | 2869 """ Runs before all tests are executed. |
2814 """ | 2870 """ |
2815 # Enable all filters, so we don't miss anything that is off by default. | 2871 # Enable all filters, so we don't miss anything that is off by default. |
2816 cpplint._DEFAULT_FILTERS = [] | 2872 cpplint._DEFAULT_FILTERS = [] |
2817 cpplint._cpplint_state.SetFilters('') | 2873 cpplint._cpplint_state.SetFilters('') |
2818 | 2874 |
2819 | 2875 |
2820 # pylint: disable-msg=C6409 | 2876 # pylint: disable-msg=C6409 |
(...skipping 18 matching lines...) Expand all Loading... |
2839 # we're running the full test suite: if we only run one test, | 2895 # we're running the full test suite: if we only run one test, |
2840 # obviously we're not going to see all the error categories. So we | 2896 # obviously we're not going to see all the error categories. So we |
2841 # only run VerifyAllCategoriesAreSeen() when no commandline flags | 2897 # only run VerifyAllCategoriesAreSeen() when no commandline flags |
2842 # are passed in. | 2898 # are passed in. |
2843 global _run_verifyallcategoriesseen | 2899 global _run_verifyallcategoriesseen |
2844 _run_verifyallcategoriesseen = (len(sys.argv) == 1) | 2900 _run_verifyallcategoriesseen = (len(sys.argv) == 1) |
2845 | 2901 |
2846 setUp() | 2902 setUp() |
2847 unittest.main() | 2903 unittest.main() |
2848 tearDown() | 2904 tearDown() |
OLD | NEW |