[clang] bdf69f6 - [Clang] Fix an unused-but-set-variable warning with volatile variable

Yonghong Song via cfe-commits cfe-commits at lists.llvm.org
Mon Mar 21 14:59:15 PDT 2022


Author: Yonghong Song
Date: 2022-03-21T14:59:03-07:00
New Revision: bdf69f63df2cf4c9e3cd1af5cfcd503bc8e2869b

URL: https://github.com/llvm/llvm-project/commit/bdf69f63df2cf4c9e3cd1af5cfcd503bc8e2869b
DIFF: https://github.com/llvm/llvm-project/commit/bdf69f63df2cf4c9e3cd1af5cfcd503bc8e2869b.diff

LOG: [Clang] Fix an unused-but-set-variable warning with volatile variable

For the following code,
    void test() {
        volatile int j = 0;
        for (int i = 0; i < 1000; i++)
                j += 1;
        return;
    }
If compiled with
    clang -g -Wall -Werror -S -emit-llvm test.c
we will see the following error:
    test.c:2:6: error: variable 'j' set but not used [-Werror,-Wunused-but-set-variable]
            volatile int j = 0;
                         ^

This is not quite right since 'j' is indeed used due to '+=' operator.
gcc doesn't emit error either in this case.
Also if we change 'j += 1' to 'j++', the warning will disappear
with latest clang.

Note that clang will issue the warning if the volatile declaration
involves only simple assignment (var = ...).

To fix the issue, in function MaybeDecrementCount(), if the
operator is a compound assignment (i.e., +=, -=, etc.) and the
variable is volatile, the count for RefsMinusAssignments will be
decremented, similar to 'j++' case.

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

Added: 
    

Modified: 
    clang/lib/Sema/SemaExprCXX.cpp
    clang/test/Sema/warn-unused-but-set-variables.c

Removed: 
    


################################################################################
diff  --git a/clang/lib/Sema/SemaExprCXX.cpp b/clang/lib/Sema/SemaExprCXX.cpp
index ee4bff5c14b89..c923dddb9f285 100644
--- a/clang/lib/Sema/SemaExprCXX.cpp
+++ b/clang/lib/Sema/SemaExprCXX.cpp
@@ -7925,6 +7925,7 @@ ExprResult Sema::ActOnNoexceptExpr(SourceLocation KeyLoc, SourceLocation,
 static void MaybeDecrementCount(
     Expr *E, llvm::DenseMap<const VarDecl *, int> &RefsMinusAssignments) {
   DeclRefExpr *LHS = nullptr;
+  bool IsCompoundAssign = false;
   if (BinaryOperator *BO = dyn_cast<BinaryOperator>(E)) {
     if (BO->getLHS()->getType()->isDependentType() ||
         BO->getRHS()->getType()->isDependentType()) {
@@ -7932,6 +7933,8 @@ static void MaybeDecrementCount(
         return;
     } else if (!BO->isAssignmentOp())
       return;
+    else
+      IsCompoundAssign = BO->isCompoundAssignmentOp();
     LHS = dyn_cast<DeclRefExpr>(BO->getLHS());
   } else if (CXXOperatorCallExpr *COCE = dyn_cast<CXXOperatorCallExpr>(E)) {
     if (COCE->getOperator() != OO_Equal)
@@ -7943,6 +7946,10 @@ static void MaybeDecrementCount(
   VarDecl *VD = dyn_cast<VarDecl>(LHS->getDecl());
   if (!VD)
     return;
+  // Don't decrement RefsMinusAssignments if volatile variable with compound
+  // assignment (+=, ...) to avoid potential unused-but-set-variable warning.
+  if (IsCompoundAssign && VD->getType().isVolatileQualified())
+    return;
   auto iter = RefsMinusAssignments.find(VD);
   if (iter == RefsMinusAssignments.end())
     return;

diff  --git a/clang/test/Sema/warn-unused-but-set-variables.c b/clang/test/Sema/warn-unused-but-set-variables.c
index a8d2ceaa428c9..6e5b7d671711b 100644
--- a/clang/test/Sema/warn-unused-but-set-variables.c
+++ b/clang/test/Sema/warn-unused-but-set-variables.c
@@ -23,10 +23,24 @@ int f0(void) {
   int a;
   w = (a = 0);
 
+  int j = 0; // expected-warning{{variable 'j' set but not used}}
+  for (int i = 0; i < 1000; i++)
+    j += 1;
+
   // Following gcc, warn for a volatile variable.
   volatile int b; // expected-warning{{variable 'b' set but not used}}
   b = 0;
 
+  // volatile variable k is used, no warning.
+  volatile int k = 0;
+  for (int i = 0; i < 1000; i++)
+    k += 1;
+
+  // typedef of volatile type, no warning.
+  typedef volatile int volint;
+  volint l = 0;
+  l += 1;
+
   int x;
   x = 0;
   return x;


        


More information about the cfe-commits mailing list