[cfe-commits] r68110 - in /cfe/trunk: include/clang/AST/Decl.h include/clang/Basic/DiagnosticSemaKinds.td include/clang/Driver/Options.def lib/AST/Decl.cpp lib/Sema/SemaDecl.cpp tools/clang-cc/Warnings.cpp
Douglas Gregor
dgregor at apple.com
Tue Mar 31 09:35:04 PDT 2009
Author: dgregor
Date: Tue Mar 31 11:35:03 2009
New Revision: 68110
URL: http://llvm.org/viewvc/llvm-project?rev=68110&view=rev
Log:
Implement -Wmissing-prototypes. Fixes PR3911.
Modified:
cfe/trunk/include/clang/AST/Decl.h
cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
cfe/trunk/include/clang/Driver/Options.def
cfe/trunk/lib/AST/Decl.cpp
cfe/trunk/lib/Sema/SemaDecl.cpp
cfe/trunk/tools/clang-cc/Warnings.cpp
Modified: cfe/trunk/include/clang/AST/Decl.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/AST/Decl.h?rev=68110&r1=68109&r2=68110&view=diff
==============================================================================
--- cfe/trunk/include/clang/AST/Decl.h (original)
+++ cfe/trunk/include/clang/AST/Decl.h Tue Mar 31 11:35:03 2009
@@ -670,6 +670,9 @@
/// external, C linkage.
bool isExternC(ASTContext &Context) const;
+ /// \brief Determines whether this is a global function.
+ bool isGlobal() const;
+
/// getPreviousDeclaration - Return the previous declaration of this
/// function.
const FunctionDecl *getPreviousDeclaration() const {
Modified: cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td?rev=68110&r1=68109&r2=68110&view=diff
==============================================================================
--- cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td (original)
+++ cfe/trunk/include/clang/Basic/DiagnosticSemaKinds.td Tue Mar 31 11:35:03 2009
@@ -712,6 +712,7 @@
def warn_unavailable : Warning<"%0 is unavailable">;
def note_unavailable_here : Note<
"function has been explicitly marked %select{unavailable|deleted}0 here">;
+def warn_missing_prototype : Warning<"no previous prototype for function %0">;
def err_redefinition : Error<"redefinition of %0">;
def err_static_non_static : Error<
"static declaration of %0 follows non-static declaration">;
Modified: cfe/trunk/include/clang/Driver/Options.def
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Driver/Options.def?rev=68110&r1=68109&r2=68110&view=diff
==============================================================================
--- cfe/trunk/include/clang/Driver/Options.def (original)
+++ cfe/trunk/include/clang/Driver/Options.def Tue Mar 31 11:35:03 2009
@@ -276,12 +276,14 @@
OPTION("-Wint-to-pointer-cast", Wint_to_pointer_cast, Flag, clang_ignored_W_Group, INVALID, "", 0)
OPTION("-Wl,", Wl_COMMA, CommaJoined, INVALID, INVALID, "li", 0)
OPTION("-Wmissing-braces", Wmissing_braces, Flag, clang_ignored_W_Group, INVALID, "", 0)
+OPTION("-Wmissing-prototypes", Wmissing_prototypes, Flag, clang_W_Group, INVALID, "", 0)
OPTION("-Wmost", Wmost, Flag, clang_ignored_W_Group, INVALID, "", 0)
OPTION("-Wnested-externs", Wnested_externs, Flag, clang_ignored_W_Group, INVALID, "", 0)
OPTION("-Wno-format-nonliteral", Wno_format_nonliteral, Flag, clang_W_Group, INVALID, "", 0)
OPTION("-Wno-format-y2k", Wno_format_y2k, Flag, clang_ignored_W_Group, INVALID, "", 0)
OPTION("-Wno-four-char-constants", Wno_four_char_constants, Flag, clang_ignored_W_Group, INVALID, "", 0)
OPTION("-Wno-missing-field-initializers", Wno_missing_field_initializers, Flag, clang_ignored_W_Group, INVALID, "", 0)
+OPTION("-Wno-missing-prototypes", Wno_missing_prototypes, Flag, clang_W_Group, INVALID, "", 0)
OPTION("-Wno-nonportable-cfstrings", Wno_nonportable_cfstrings, Joined, W_Group, INVALID, "", 0)
OPTION("-Wno-pointer-sign", Wno_pointer_sign, Flag, clang_W_Group, INVALID, "", 0)
OPTION("-Wno-strict-selector-match", Wno_strict_selector_match, Flag, clang_W_Group, INVALID, "", 0)
Modified: cfe/trunk/lib/AST/Decl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/AST/Decl.cpp?rev=68110&r1=68109&r2=68110&view=diff
==============================================================================
--- cfe/trunk/lib/AST/Decl.cpp (original)
+++ cfe/trunk/lib/AST/Decl.cpp Tue Mar 31 11:35:03 2009
@@ -341,6 +341,26 @@
return false;
}
+bool FunctionDecl::isGlobal() const {
+ if (const CXXMethodDecl *Method = dyn_cast<CXXMethodDecl>(this))
+ return Method->isStatic();
+
+ if (getStorageClass() == Static)
+ return false;
+
+ for (const DeclContext *DC = getDeclContext();
+ DC->isNamespace();
+ DC = DC->getParent()) {
+ if (const NamespaceDecl *Namespace = cast<NamespaceDecl>(DC)) {
+ if (!Namespace->getDeclName())
+ return false;
+ break;
+ }
+ }
+
+ return true;
+}
+
/// \brief Returns a value indicating whether this function
/// corresponds to a builtin function.
///
Modified: cfe/trunk/lib/Sema/SemaDecl.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDecl.cpp?rev=68110&r1=68109&r2=68110&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDecl.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDecl.cpp Tue Mar 31 11:35:03 2009
@@ -2741,6 +2741,28 @@
diag::err_func_def_incomplete_result))
FD->setInvalidDecl();
+ // GNU warning -Wmissing-prototypes:
+ // Warn if a global function is defined without a previous
+ // prototype declaration. This warning is issued even if the
+ // definition itself provides a prototype. The aim is to detect
+ // global functions that fail to be declared in header files.
+ if (!FD->isInvalidDecl() && FD->isGlobal() && !isa<CXXMethodDecl>(FD)) {
+ bool MissingPrototype = true;
+ for (const FunctionDecl *Prev = FD->getPreviousDeclaration();
+ Prev; Prev = Prev->getPreviousDeclaration()) {
+ // Ignore any declarations that occur in function or method
+ // scope, because they aren't visible from the header.
+ if (Prev->getDeclContext()->isFunctionOrMethod())
+ continue;
+
+ MissingPrototype = !Prev->getType()->isFunctionProtoType();
+ break;
+ }
+
+ if (MissingPrototype)
+ Diag(FD->getLocation(), diag::warn_missing_prototype) << FD;
+ }
+
PushDeclContext(FnBodyScope, FD);
// Check the validity of our function parameters
Modified: cfe/trunk/tools/clang-cc/Warnings.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/tools/clang-cc/Warnings.cpp?rev=68110&r1=68109&r2=68110&view=diff
==============================================================================
--- cfe/trunk/tools/clang-cc/Warnings.cpp (original)
+++ cfe/trunk/tools/clang-cc/Warnings.cpp Tue Mar 31 11:35:03 2009
@@ -140,6 +140,9 @@
diag::ext_typecheck_convert_incompatible_pointer_sign
};
static const diag::kind DeprecatedDeclarations[] = { diag::warn_deprecated };
+static const diag::kind MissingPrototypesDiags[] = {
+ diag::warn_missing_prototype
+};
// Hmm ... this option is currently actually completely ignored.
//static const diag::kind StrictSelectorMatchDiags[] = { };
@@ -149,6 +152,7 @@
{ "float-equal", DIAGS(FloatEqualDiags) },
{ "format-nonliteral", DIAGS(FormatNonLiteralDiags) },
{ "implicit-function-declaration", DIAGS(ImplicitFunctionDeclarationDiags) },
+ { "missing-prototypes", DIAGS(MissingPrototypesDiags) },
{ "pointer-sign", DIAGS(PointerSignDiags) },
{ "readonly-setter-attrs", DIAGS(ReadOnlySetterAttrsDiags) },
{ "undef", DIAGS(UndefDiags) },
@@ -179,6 +183,7 @@
Diags.setDiagnosticMapping(diag::err_pp_file_not_found, diag::MAP_FATAL);
Diags.setDiagnosticMapping(diag::err_template_recursion_depth_exceeded,
diag::MAP_FATAL);
+ Diags.setDiagnosticMapping(diag::warn_missing_prototype, diag::MAP_IGNORE);
Diags.setSuppressSystemWarnings(!OptWarnInSystemHeaders);
for (OptionsList::iterator it = Options.begin(), e = Options.end();
More information about the cfe-commits
mailing list