File tree Expand file tree Collapse file tree 5 files changed +59
-4
lines changed
Expand file tree Collapse file tree 5 files changed +59
-4
lines changed Original file line number Diff line number Diff line change @@ -555,15 +555,22 @@ bool NarrowingConversionsCheck::handleConditionalOperator(
555555 // We have an expression like so: `output = cond ? lhs : rhs`
556556 // From the point of view of narrowing conversion we treat it as two
557557 // expressions `output = lhs` and `output = rhs`.
558- handleBinaryOperator (Context, CO->getLHS ()->getExprLoc (), Lhs,
559- *CO->getLHS ());
560- handleBinaryOperator (Context, CO->getRHS ()->getExprLoc (), Lhs,
561- *CO->getRHS ());
558+ handleConditionalOperatorArgument (Context, Lhs, CO->getLHS ());
559+ handleConditionalOperatorArgument (Context, Lhs, CO->getRHS ());
562560 return true ;
563561 }
564562 return false ;
565563}
566564
565+ void NarrowingConversionsCheck::handleConditionalOperatorArgument (
566+ const ASTContext &Context, const Expr &Lhs, const Expr *Arg) {
567+ if (const auto *ICE = llvm::dyn_cast<ImplicitCastExpr>(Arg))
568+ if (!Arg->getIntegerConstantExpr (Context))
569+ Arg = ICE->getSubExpr ();
570+
571+ handleBinaryOperator (Context, Arg->getExprLoc (), Lhs, *Arg);
572+ }
573+
567574void NarrowingConversionsCheck::handleImplicitCast (
568575 const ASTContext &Context, const ImplicitCastExpr &Cast) {
569576 if (Cast.getExprLoc ().isMacroID ())
Original file line number Diff line number Diff line change @@ -85,6 +85,8 @@ class NarrowingConversionsCheck : public ClangTidyCheck {
8585 bool handleConditionalOperator (const ASTContext &Context, const Expr &Lhs,
8686 const Expr &Rhs);
8787
88+ void handleConditionalOperatorArgument (const ASTContext &Context,
89+ const Expr &Lhs, const Expr *Arg);
8890 void handleImplicitCast (const ASTContext &Context,
8991 const ImplicitCastExpr &Cast);
9092
Original file line number Diff line number Diff line change @@ -134,6 +134,10 @@ Changes in existing checks
134134 <clang-tidy/checks/bugprone/infinite-loop>` check by adding detection for
135135 variables introduced by structured bindings.
136136
137+ - Improved :doc: `bugprone-narrowing-conversions
138+ <clang-tidy/checks/bugprone/narrowing-conversions>` check by fixing
139+ false positive from analysis of a conditional expression in C.
140+
137141- Improved :doc: `bugprone-reserved-identifier
138142 <clang-tidy/checks/bugprone/reserved-identifier>` check by ignoring
139143 declarations in system headers.
Original file line number Diff line number Diff line change 1+ // RUN: %check_clang_tidy %s bugprone-narrowing-conversions %t -- --
2+
3+ char test_char (int cond , char c ) {
4+ char ret = cond > 0 ? ':' : c ;
5+ return ret ;
6+ }
7+
8+ short test_short (int cond , short s ) {
9+ short ret = cond > 0 ? ':' : s ;
10+ return ret ;
11+ }
12+
13+ int test_int (int cond , int i ) {
14+ int ret = cond > 0 ? ':' : i ;
15+ return ret ;
16+ }
17+
18+ void test (int cond , int i ) {
19+ char x = cond > 0 ? ':' : i ;
20+ // CHECK-MESSAGES: :[[@LINE-1]]:29: warning: narrowing conversion from 'int' to signed type 'char' is implementation-defined [bugprone-narrowing-conversions]
21+ }
Original file line number Diff line number Diff line change 1+ // RUN: %check_clang_tidy %s bugprone-narrowing-conversions %t -- --
2+
3+ char test_char (int cond, char c) {
4+ char ret = cond > 0 ? ' :' : c;
5+ return ret;
6+ }
7+
8+ short test_short (int cond, short s) {
9+ short ret = cond > 0 ? ' :' : s;
10+ return ret;
11+ }
12+
13+ int test_int (int cond, int i) {
14+ int ret = cond > 0 ? ' :' : i;
15+ return ret;
16+ }
17+
18+ void test (int cond, int i) {
19+ char x = cond > 0 ? ' :' : i;
20+ // CHECK-MESSAGES: :[[@LINE-1]]:29: warning: narrowing conversion from 'int' to signed type 'char' is implementation-defined [bugprone-narrowing-conversions]
21+ }
You can’t perform that action at this time.
0 commit comments