According to Doug this is ok behavior. The rational is that why did the user bother to define the function if the definition was never used? Seems ok to warn.

-Tanya

On Fri, 12 Feb 2010, Daniel Dunbar wrote:

Hi Tanya,

This is giving a false positive on the following code, can you take a look?

--
ddun...@lordcrumb:tmp$ cat t.c
static void f0(void);
void f1(void(*a0)(void));
void f2(void) { f1(f0); }
static void f0(void) {}
ddun...@lordcrumb:tmp$ clang -Wunused-function -fsyntax-only t.c
t.c:4:13: warning: unused function 'f0' [-Wunused-function]
static void f0(void) {}
           ^
1 diagnostic generated.
ddun...@lordcrumb:tmp$
--

- Daniel

On Thu, Feb 11, 2010 at 4:07 PM, Tanya Lattner <[email protected]> wrote:
Author: tbrethou
Date: Thu Feb 11 18:07:30 2010
New Revision: 95940

URL: http://llvm.org/viewvc/llvm-project?rev=95940&view=rev
Log:
Implementing unused function warning.

Added:
   cfe/trunk/test/Sema/warn-unused-function.c
Modified:
   cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
   cfe/trunk/include/clang/Frontend/PCHBitCodes.h
   cfe/trunk/include/clang/Frontend/PCHReader.h
   cfe/trunk/lib/Frontend/PCHReader.cpp
   cfe/trunk/lib/Frontend/PCHWriter.cpp
   cfe/trunk/lib/Sema/Sema.cpp
   cfe/trunk/lib/Sema/Sema.h
   cfe/trunk/lib/Sema/SemaDecl.cpp
   cfe/trunk/lib/Sema/SemaExpr.cpp

Modified: cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td (original)
+++ cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td Thu Feb 11 18:07:30 
2010
@@ -87,7 +87,9 @@
  "declaration of %0 will not be visible outside of this function">;
 def err_array_star_in_function_definition : Error<
  "variable length array must be bound in function definition">;
-
+def warn_unused_function : Warning<"unused function %0">,
+  InGroup<UnusedFunction>, DefaultIgnore;
+
 def warn_implicit_function_decl : Warning<
  "implicit declaration of function %0">,
  InGroup<ImplicitFunctionDeclare>, DefaultIgnore;

Modified: cfe/trunk/include/clang/Frontend/PCHBitCodes.h
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Frontend/PCHBitCodes.h?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/include/clang/Frontend/PCHBitCodes.h (original)
+++ cfe/trunk/include/clang/Frontend/PCHBitCodes.h Thu Feb 11 18:07:30 2010
@@ -221,7 +221,11 @@

      /// \brief Record code for the version control branch and revision
      /// information of the compiler used to build this PCH file.
-      VERSION_CONTROL_BRANCH_REVISION = 21
+      VERSION_CONTROL_BRANCH_REVISION = 21,
+
+      /// \brief Record code for the array of unused static functions.
+      UNUSED_STATIC_FUNCS = 22
+
    };

    /// \brief Record types used within a source manager block.

Modified: cfe/trunk/include/clang/Frontend/PCHReader.h
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Frontend/PCHReader.h?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/include/clang/Frontend/PCHReader.h (original)
+++ cfe/trunk/include/clang/Frontend/PCHReader.h Thu Feb 11 18:07:30 2010
@@ -306,6 +306,10 @@
  /// \brief The set of tentative definitions stored in the the PCH
  /// file.
  llvm::SmallVector<uint64_t, 16> TentativeDefinitions;
+
+  /// \brief The set of tentative definitions stored in the the PCH
+  /// file.
+  llvm::SmallVector<uint64_t, 16> UnusedStaticFuncs;

  /// \brief The set of locally-scoped external declarations stored in
  /// the the PCH file.

Modified: cfe/trunk/lib/Frontend/PCHReader.cpp
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Frontend/PCHReader.cpp?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/lib/Frontend/PCHReader.cpp (original)
+++ cfe/trunk/lib/Frontend/PCHReader.cpp Thu Feb 11 18:07:30 2010
@@ -1332,6 +1332,14 @@
      TentativeDefinitions.swap(Record);
      break;

+    case pch::UNUSED_STATIC_FUNCS:
+      if (!UnusedStaticFuncs.empty()) {
+        Error("duplicate UNUSED_STATIC_FUNCS record in PCH file");
+        return Failure;
+      }
+      UnusedStaticFuncs.swap(Record);
+      break;
+
    case pch::LOCALLY_SCOPED_EXTERNAL_DECLS:
      if (!LocallyScopedExternalDecls.empty()) {
        Error("duplicate LOCALLY_SCOPED_EXTERNAL_DECLS record in PCH file");
@@ -2479,6 +2487,13 @@
    VarDecl *Var = cast<VarDecl>(GetDecl(TentativeDefinitions[I]));
    SemaObj->TentativeDefinitions.push_back(Var);
  }
+
+  // If there were any unused static functions, deserialize them and add to
+  // Sema's list of unused static functions.
+  for (unsigned I = 0, N = UnusedStaticFuncs.size(); I != N; ++I) {
+    FunctionDecl *FD = cast<FunctionDecl>(GetDecl(UnusedStaticFuncs[I]));
+    SemaObj->UnusedStaticFuncs.push_back(FD);
+  }

  // If there were any locally-scoped external declarations,
  // deserialize them and add them to Sema's table of locally-scoped

Modified: cfe/trunk/lib/Frontend/PCHWriter.cpp
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Frontend/PCHWriter.cpp?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/lib/Frontend/PCHWriter.cpp (original)
+++ cfe/trunk/lib/Frontend/PCHWriter.cpp Thu Feb 11 18:07:30 2010
@@ -545,6 +545,7 @@
  RECORD(SPECIAL_TYPES);
  RECORD(STATISTICS);
  RECORD(TENTATIVE_DEFINITIONS);
+  RECORD(UNUSED_STATIC_FUNCS);
  RECORD(LOCALLY_SCOPED_EXTERNAL_DECLS);
  RECORD(SELECTOR_OFFSETS);
  RECORD(METHOD_POOL);
@@ -1982,6 +1983,11 @@
    AddDeclRef(SemaRef.TentativeDefinitions[i], TentativeDefinitions);
  }

+  // Build a record containing all of the static unused functions in this file.
+  RecordData UnusedStaticFuncs;
+  for (unsigned i=0, e = SemaRef.UnusedStaticFuncs.size(); i !=e; ++i)
+    AddDeclRef(SemaRef.UnusedStaticFuncs[i], UnusedStaticFuncs);
+
  // Build a record containing all of the locally-scoped external
  // declarations in this header file. Generally, this record will be
  // empty.
@@ -2083,6 +2089,10 @@
  if (!TentativeDefinitions.empty())
    Stream.EmitRecord(pch::TENTATIVE_DEFINITIONS, TentativeDefinitions);

+  // Write the record containing unused static functions.
+  if (!UnusedStaticFuncs.empty())
+    Stream.EmitRecord(pch::UNUSED_STATIC_FUNCS, UnusedStaticFuncs);
+
  // Write the record containing locally-scoped external definitions.
  if (!LocallyScopedExternalDecls.empty())
    Stream.EmitRecord(pch::LOCALLY_SCOPED_EXTERNAL_DECLS,

Modified: cfe/trunk/lib/Sema/Sema.cpp
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/Sema.cpp?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/Sema.cpp (original)
+++ cfe/trunk/lib/Sema/Sema.cpp Thu Feb 11 18:07:30 2010
@@ -185,6 +185,12 @@
 /// popped.
 void Sema::ActOnEndOfTranslationUnit() {

+  // Remove functions that turned out to be used.
+  UnusedStaticFuncs.erase(std::remove_if(UnusedStaticFuncs.begin(),
+                                         UnusedStaticFuncs.end(),
+                                         std::mem_fun(&FunctionDecl::isUsed)),
+                          UnusedStaticFuncs.end());
+
  while (1) {
    // C++: Perform implicit template instantiations.
    //
@@ -265,6 +271,15 @@
      Consumer.CompleteTentativeDefinition(VD);

  }
+
+  // Output warning for unused functions.
+  for (std::vector<FunctionDecl*>::iterator
+       F = UnusedStaticFuncs.begin(),
+       FEnd = UnusedStaticFuncs.end();
+       F != FEnd;
+       ++F)
+    Diag((*F)->getLocation(), diag::warn_unused_function) << 
(*F)->getDeclName();
+
 }



Modified: cfe/trunk/lib/Sema/Sema.h
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/Sema.h?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/Sema.h (original)
+++ cfe/trunk/lib/Sema/Sema.h Thu Feb 11 18:07:30 2010
@@ -276,6 +276,9 @@
  /// \brief All the tentative definitions encountered in the TU.
  std::vector<VarDecl *> TentativeDefinitions;

+  /// \brief The set of static functions seen so far that have not been used.
+  std::vector<FunctionDecl*> UnusedStaticFuncs;
+
  /// An enum describing the kind of diagnostics to use when checking
  /// access.
  enum AccessDiagnosticsKind {

Modified: cfe/trunk/lib/Sema/SemaDecl.cpp
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDecl.cpp?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/SemaDecl.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDecl.cpp Thu Feb 11 18:07:30 2010
@@ -3129,6 +3129,15 @@
  if (FunctionTemplate)
    return FunctionTemplate;

+
+  // Keep track of static, non-inlined function definitions that
+  // have not been used. We will warn later.
+  // FIXME: Also include static functions declared but not defined.
+  if (!NewFD->isInvalidDecl() && IsFunctionDefinition
+      && !NewFD->isInlined() && NewFD->getLinkage() == InternalLinkage
+      && !NewFD->isUsed())
+    UnusedStaticFuncs.push_back(NewFD);
+
  return NewFD;
 }


Modified: cfe/trunk/lib/Sema/SemaExpr.cpp
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=95940&r1=95939&r2=95940&view=diff

==============================================================================
--- cfe/trunk/lib/Sema/SemaExpr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExpr.cpp Thu Feb 11 18:07:30 2010
@@ -7293,6 +7293,7 @@

    // FIXME: keep track of references to static functions
    Function->setUsed(true);
+
    return;
  }


Added: cfe/trunk/test/Sema/warn-unused-function.c
URL: 
http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/warn-unused-function.c?rev=95940&view=auto

==============================================================================
--- cfe/trunk/test/Sema/warn-unused-function.c (added)
+++ cfe/trunk/test/Sema/warn-unused-function.c Thu Feb 11 18:07:30 2010
@@ -0,0 +1,16 @@
+// RUN: %clang_cc1 -fsyntax-only -Wunused-function -verify %s
+
+void foo() {}
+static void f2() {}
+static void f1() {f2();} // expected-warning{{unused}}
+
+static int f0() { return 17; } // expected-warning{{unused}}
+int x = sizeof(f0());
+
+static void f3();
+extern void f3() { } // expected-warning{{unused}}
+
+// FIXME: This will trigger a warning when it should not.
+// Update once PR6281 is fixed.
+//inline static void f4();
+//void f4() { }
\ No newline at end of file


_______________________________________________
cfe-commits mailing list
[email protected]
http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits

_______________________________________________
cfe-commits mailing list
[email protected]
http://lists.cs.uiuc.edu/mailman/listinfo/cfe-commits

Reply via email to