r316830 - [analyzer] LoopUnrolling: check the bitwidth of the used numbers (pr34943)

Peter Szecsi via cfe-commits cfe-commits at lists.llvm.org
Sat Oct 28 05:19:08 PDT 2017


Author: szepet
Date: Sat Oct 28 05:19:08 2017
New Revision: 316830

URL: http://llvm.org/viewvc/llvm-project?rev=316830&view=rev
Log:
[analyzer] LoopUnrolling: check the bitwidth of the used numbers (pr34943)

The loop unrolling feature aims to track the maximum possible steps a loop can
make. In order to implement this, it investigates the initial value of the 
counter variable and the bound number. (It has to be known.)
These numbers are used as llvm::APInts, however, it was not checked if their
bitwidths are the same which lead to some crashes.
This revision solves this problem by extending the "shorter" one (to the length
of the "longer" one).
For the detailed bug report, see: https://bugs.llvm.org/show_bug.cgi?id=34943

Differential Revision: https://reviews.llvm.org/D38922


Modified:
    cfe/trunk/lib/StaticAnalyzer/Core/LoopUnrolling.cpp
    cfe/trunk/test/Analysis/loop-unrolling.cpp

Modified: cfe/trunk/lib/StaticAnalyzer/Core/LoopUnrolling.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/StaticAnalyzer/Core/LoopUnrolling.cpp?rev=316830&r1=316829&r2=316830&view=diff
==============================================================================
--- cfe/trunk/lib/StaticAnalyzer/Core/LoopUnrolling.cpp (original)
+++ cfe/trunk/lib/StaticAnalyzer/Core/LoopUnrolling.cpp Sat Oct 28 05:19:08 2017
@@ -208,9 +208,16 @@ bool shouldCompletelyUnroll(const Stmt *
     return false;
 
   auto CounterVar = Matches[0].getNodeAs<VarDecl>("initVarName");
-  auto BoundNum = Matches[0].getNodeAs<IntegerLiteral>("boundNum")->getValue();
-  auto InitNum = Matches[0].getNodeAs<IntegerLiteral>("initNum")->getValue();
+  llvm::APInt BoundNum =
+      Matches[0].getNodeAs<IntegerLiteral>("boundNum")->getValue();
+  llvm::APInt InitNum =
+      Matches[0].getNodeAs<IntegerLiteral>("initNum")->getValue();
   auto CondOp = Matches[0].getNodeAs<BinaryOperator>("conditionOperator");
+  if (InitNum.getBitWidth() != BoundNum.getBitWidth()) {
+    InitNum = InitNum.zextOrSelf(BoundNum.getBitWidth());
+    BoundNum = BoundNum.zextOrSelf(InitNum.getBitWidth());
+  }
+
   if (CondOp->getOpcode() == BO_GE || CondOp->getOpcode() == BO_LE)
     maxStep = (BoundNum - InitNum + 1).abs().getZExtValue();
   else

Modified: cfe/trunk/test/Analysis/loop-unrolling.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Analysis/loop-unrolling.cpp?rev=316830&r1=316829&r2=316830&view=diff
==============================================================================
--- cfe/trunk/test/Analysis/loop-unrolling.cpp (original)
+++ cfe/trunk/test/Analysis/loop-unrolling.cpp Sat Oct 28 05:19:08 2017
@@ -373,3 +373,9 @@ int num_steps_over_limit3() {
   return 0;
 }
 
+
+void pr34943() {
+  for (int i = 0; i < 6L; ++i) {
+    clang_analyzer_numTimesReached(); // expected-warning {{6}}
+  }
+}




More information about the cfe-commits mailing list