diff options
| author | Daniel Marjamaki <daniel.marjamaki@evidente.se> | 2016-06-08 10:30:24 +0000 |
|---|---|---|
| committer | Daniel Marjamaki <daniel.marjamaki@evidente.se> | 2016-06-08 10:30:24 +0000 |
| commit | 8ba0233e467f833211a7bc43ad849094aabe8e81 (patch) | |
| tree | f4bcb6ff8b1dbe9f93ffcb0d68aa4f7ca6c8f8a7 /clang-tools-extra/clang-tidy/misc/MacroParenthesesCheck.cpp | |
| parent | 0781d10ac44018e7067bcdbf8e1b20cb5c497703 (diff) | |
| download | bcm5719-llvm-8ba0233e467f833211a7bc43ad849094aabe8e81.tar.gz bcm5719-llvm-8ba0233e467f833211a7bc43ad849094aabe8e81.zip | |
[clang-tidy] misc-macro-parentheses - avoid adding parentheses in variable declarations
Fixes bugzilla issues 26273 and 27399
Reviewers: alexfh
Subscribers: cfe-commits
Differential Revision: http://reviews.llvm.org/D20853
llvm-svn: 272128
Diffstat (limited to 'clang-tools-extra/clang-tidy/misc/MacroParenthesesCheck.cpp')
| -rw-r--r-- | clang-tools-extra/clang-tidy/misc/MacroParenthesesCheck.cpp | 51 |
1 files changed, 49 insertions, 2 deletions
diff --git a/clang-tools-extra/clang-tidy/misc/MacroParenthesesCheck.cpp b/clang-tools-extra/clang-tidy/misc/MacroParenthesesCheck.cpp index 1cd6bbf6e66..ebfb8c03298 100644 --- a/clang-tools-extra/clang-tidy/misc/MacroParenthesesCheck.cpp +++ b/clang-tools-extra/clang-tidy/misc/MacroParenthesesCheck.cpp @@ -19,8 +19,7 @@ namespace misc { namespace { class MacroParenthesesPPCallbacks : public PPCallbacks { public: - MacroParenthesesPPCallbacks(Preprocessor *PP, - MacroParenthesesCheck *Check) + MacroParenthesesPPCallbacks(Preprocessor *PP, MacroParenthesesCheck *Check) : PP(PP), Check(Check) {} void MacroDefined(const Token &MacroNameTok, @@ -67,8 +66,46 @@ static bool isWarnOp(const Token &T) { tok::amp, tok::pipe, tok::caret); } +/// Is given Token a keyword that is used in variable declarations? +static bool isVarDeclKeyword(const Token &T) { + return T.isOneOf(tok::kw_bool, tok::kw_char, tok::kw_short, tok::kw_int, + tok::kw_long, tok::kw_float, tok::kw_double, tok::kw_const, + tok::kw_enum, tok::kw_inline, tok::kw_static, tok::kw_struct, + tok::kw_signed, tok::kw_unsigned); +} + +/// Is there a possible variable declaration at Tok? +static bool possibleVarDecl(const MacroInfo *MI, const Token *Tok) { + if (Tok == MI->tokens_end()) + return false; + + // If we see int/short/struct/etc., just assume this is a variable declaration. + if (isVarDeclKeyword(*Tok)) + return true; + + // Variable declarations start with identifier or coloncolon. + if (!Tok->isOneOf(tok::identifier, tok::raw_identifier, tok::coloncolon)) + return false; + + // Skip possible types, etc + while ( + Tok != MI->tokens_end() && + Tok->isOneOf(tok::identifier, tok::raw_identifier, tok::coloncolon, + tok::star, tok::amp, tok::ampamp, tok::less, tok::greater)) + Tok++; + + // Return true for possible variable declarations. + return Tok == MI->tokens_end() || + Tok->isOneOf(tok::equal, tok::semi, tok::l_square, tok::l_paren) || + isVarDeclKeyword(*Tok); +} + void MacroParenthesesPPCallbacks::replacementList(const Token &MacroNameTok, const MacroInfo *MI) { + // Make sure macro replacement isn't a variable declaration. + if (possibleVarDecl(MI, MI->tokens_begin())) + return; + // Count how deep we are in parentheses/braces/squares. int Count = 0; @@ -117,6 +154,9 @@ void MacroParenthesesPPCallbacks::replacementList(const Token &MacroNameTok, void MacroParenthesesPPCallbacks::argument(const Token &MacroNameTok, const MacroInfo *MI) { + + // Skip variable declaration. + bool VarDecl = possibleVarDecl(MI, MI->tokens_begin()); for (auto TI = MI->tokens_begin(), TE = MI->tokens_end(); TI != TE; ++TI) { // First token. @@ -132,6 +172,13 @@ void MacroParenthesesPPCallbacks::argument(const Token &MacroNameTok, const Token &Tok = *TI; + // There should not be extra parentheses in possible variable declaration. + if (VarDecl) { + if (Tok.isOneOf(tok::equal, tok::semi, tok::l_square, tok::l_paren)) + VarDecl = false; + continue; + } + // Only interested in identifiers. if (!Tok.isOneOf(tok::identifier, tok::raw_identifier)) continue; |

