-
Notifications
You must be signed in to change notification settings - Fork 11k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
[clang-tidy] introduce modernize-deprecated-headers check
Summary: This patch introduces the modernize-deprecated-headers check, which is supposed to replace deprecated C library headers with the C++ STL-ones. For information see documentation; for exmaples see the test cases. Reviewers: Eugene.Zelenko, LegalizeAdulthood, alexfh Subscribers: cfe-commits Patch by Kirill Bobyrev! Differential Revision: http://reviews.llvm.org/D17484 llvm-svn: 261738
- Loading branch information
Showing
8 changed files
with
512 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
110 changes: 110 additions & 0 deletions
110
clang-tools-extra/clang-tidy/modernize/DeprecatedHeadersCheck.cpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,110 @@ | ||
//===--- DeprecatedHeadersCheck.cpp - clang-tidy---------------------------===// | ||
// | ||
// The LLVM Compiler Infrastructure | ||
// | ||
// This file is distributed under the University of Illinois Open Source | ||
// License. See LICENSE.TXT for details. | ||
// | ||
//===----------------------------------------------------------------------===// | ||
|
||
#include "DeprecatedHeadersCheck.h" | ||
#include "clang/Frontend/CompilerInstance.h" | ||
#include "clang/Lex/PPCallbacks.h" | ||
#include "clang/Lex/Preprocessor.h" | ||
#include "llvm/ADT/StringMap.h" | ||
|
||
#include <vector> | ||
|
||
namespace clang { | ||
namespace tidy { | ||
namespace modernize { | ||
|
||
namespace { | ||
class IncludeModernizePPCallbacks : public PPCallbacks { | ||
public: | ||
explicit IncludeModernizePPCallbacks(ClangTidyCheck &Check, | ||
LangOptions LangOpts); | ||
|
||
void InclusionDirective(SourceLocation HashLoc, const Token &IncludeTok, | ||
StringRef FileName, bool IsAngled, | ||
CharSourceRange FilenameRange, const FileEntry *File, | ||
StringRef SearchPath, StringRef RelativePath, | ||
const Module *Imported) override; | ||
|
||
private: | ||
ClangTidyCheck &Check; | ||
LangOptions LangOpts; | ||
llvm::StringMap<std::string> CStyledHeaderToCxx; | ||
}; | ||
} // namespace | ||
|
||
void DeprecatedHeadersCheck::registerPPCallbacks(CompilerInstance &Compiler) { | ||
if (this->getLangOpts().CPlusPlus) { | ||
Compiler.getPreprocessor().addPPCallbacks( | ||
::llvm::make_unique<IncludeModernizePPCallbacks>(*this, | ||
this->getLangOpts())); | ||
} | ||
} | ||
|
||
IncludeModernizePPCallbacks::IncludeModernizePPCallbacks(ClangTidyCheck &Check, | ||
LangOptions LangOpts) | ||
: Check(Check), LangOpts(LangOpts), | ||
CStyledHeaderToCxx({{"assert.h", "cassert"}, | ||
{"complex.h", "ccomplex"}, | ||
{"ctype.h", "cctype"}, | ||
{"errno.h", "cerrno"}, | ||
{"float.h", "cfloat"}, | ||
{"inttypes.h", "cinttypes"}, | ||
{"iso646.h", "ciso646"}, | ||
{"limits.h", "climits"}, | ||
{"locale.h", "clocale"}, | ||
{"math.h", "cmath"}, | ||
{"setjmp.h", "csetjmp"}, | ||
{"signal.h", "csignal"}, | ||
{"stdarg.h", "cstdarg"}, | ||
{"stddef.h", "cstddef"}, | ||
{"stdint.h", "cstdint"}, | ||
{"stdio.h", "cstdio"}, | ||
{"stdlib.h", "cstdlib"}, | ||
{"string.h", "cstring"}, | ||
{"time.h", "ctime"}, | ||
{"wchar.h", "cwchar"}, | ||
{"wctype.h", "cwctype"}}) { | ||
// Add C++ 11 headers. | ||
if (LangOpts.CPlusPlus11) { | ||
for (const auto &it : std::vector<std::pair<std::string, std::string>>( | ||
{{"fenv.h", "cfenv"}, | ||
{"stdalign.h", "cstdalign"}, | ||
{"stdbool.h", "cstdbool"}, | ||
{"tgmath.h", "ctgmath"}, | ||
{"uchar.h", "cuchar"}})) { | ||
CStyledHeaderToCxx.insert(it); | ||
} | ||
} | ||
} | ||
|
||
void IncludeModernizePPCallbacks::InclusionDirective( | ||
SourceLocation HashLoc, const Token &IncludeTok, StringRef FileName, | ||
bool IsAngled, CharSourceRange FilenameRange, const FileEntry *File, | ||
StringRef SearchPath, StringRef RelativePath, const Module *Imported) { | ||
// FIXME: Take care of library symbols from the global namespace. | ||
// | ||
// Reasonable options for the check: | ||
// | ||
// 1. Insert std prefix for every such symbol occurance. | ||
// 2. Insert `using namespace std;` to the beginning of TU. | ||
// 3. Do nothing and let the user deal with the migration himself. | ||
if (CStyledHeaderToCxx.count(FileName) != 0) { | ||
std::string Replacement = | ||
(llvm::Twine("<") + CStyledHeaderToCxx[FileName] + ">").str(); | ||
Check.diag(FilenameRange.getBegin(), | ||
"inclusion of deprecated C++ header '%0'; consider using '%1' instead") | ||
<< FileName << CStyledHeaderToCxx[FileName] | ||
<< FixItHint::CreateReplacement(FilenameRange.getAsRange(), | ||
Replacement); | ||
} | ||
} | ||
|
||
} // namespace modernize | ||
} // namespace tidy | ||
} // namespace clang |
42 changes: 42 additions & 0 deletions
42
clang-tools-extra/clang-tidy/modernize/DeprecatedHeadersCheck.h
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,42 @@ | ||
//===--- DeprecatedHeadersCheck.h - clang-tidy-------------------*- C++ -*-===// | ||
// | ||
// The LLVM Compiler Infrastructure | ||
// | ||
// This file is distributed under the University of Illinois Open Source | ||
// License. See LICENSE.TXT for details. | ||
// | ||
//===----------------------------------------------------------------------===// | ||
|
||
#ifndef LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_MODERNIZE_C_HEADERS_TO_CXX_H | ||
#define LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_MODERNIZE_C_HEADERS_TO_CXX_H | ||
|
||
#include "../ClangTidy.h" | ||
|
||
namespace clang { | ||
namespace tidy { | ||
namespace modernize { | ||
|
||
/// This check replaces deprecated C library headers with their C++ STL | ||
/// alternatives. | ||
/// | ||
/// Before: | ||
/// #include <header.h> | ||
/// After: | ||
/// #include <cheader> | ||
/// | ||
/// Example: <stdio.h> => <cstdio> | ||
/// | ||
/// For the user-facing documentation see: | ||
/// http://clang.llvm.org/extra/clang-tidy/checks/modernize-deprecated-headers.html | ||
class DeprecatedHeadersCheck : public ClangTidyCheck { | ||
public: | ||
DeprecatedHeadersCheck(StringRef Name, ClangTidyContext *Context) | ||
: ClangTidyCheck(Name, Context) {} | ||
void registerPPCallbacks(CompilerInstance &Compiler) override; | ||
}; | ||
|
||
} // namespace modernize | ||
} // namespace tidy | ||
} // namespace clang | ||
|
||
#endif // LLVM_CLANG_TOOLS_EXTRA_CLANG_TIDY_MODERNIZE_C_HEADERS_TO_CXX_H |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
45 changes: 45 additions & 0 deletions
45
clang-tools-extra/docs/clang-tidy/checks/modernize-deprecated-headers.rst
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,45 @@ | ||
.. title:: clang-tidy - modernize-deprecated-headers | ||
|
||
modernize-deprecated-headers | ||
========================== | ||
|
||
Some headers from C library were deprecated in C++ and are no longer welcome in | ||
C++ codebases. For more details refer to the C++ 14 Standard [depr.c.headers] | ||
section. | ||
|
||
This check replaces C standard library headers with their C++ alternatives. | ||
|
||
Improtant note: the Standard doesn't guarantee that the C++ headers declare all | ||
the same functions in the global namespace. The check in its current form can | ||
break the code that uses library symbols from the global namespace. | ||
|
||
* `<assert.h>` | ||
* `<complex.h>` | ||
* `<ctype.h>` | ||
* `<errno.h>` | ||
* `<fenv.h>` // deprecated since C++11 | ||
* `<float.h>` | ||
* `<inttypes.h>` | ||
* `<iso646.h>` | ||
* `<limits.h>` | ||
* `<locale.h>` | ||
* `<math.h>` | ||
* `<setjmp.h>` | ||
* `<signal.h>` | ||
* `<stdalign.h>` // deprecated since C++11 | ||
* `<stdarg.h>` | ||
* `<stdbool.h>` // deprecated since C++11 | ||
* `<stddef.h>` | ||
* `<stdint.h>` | ||
* `<stdio.h>` | ||
* `<stdlib.h>` | ||
* `<string.h>` | ||
* `<tgmath.h>` // deprecated since C++11 | ||
* `<time.h>` | ||
* `<uchar.h>` // deprecated since C++11 | ||
* `<wchar.h>` | ||
* `<wctype.h>` | ||
|
||
If the specified standard is older than C++11 the check will only replace | ||
headers deprecated before C++11, otherwise -- every header that appeared in | ||
the list. |
147 changes: 147 additions & 0 deletions
147
clang-tools-extra/test/clang-tidy/modernize-deprecated-headers-cxx03.cpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,147 @@ | ||
// RUN: %check_clang_tidy %s modernize-deprecated-headers %t -- -- -std=c++03 -isystem %S/Inputs/Headers | ||
|
||
#include <assert.h> | ||
#include <complex.h> | ||
#include <ctype.h> | ||
#include <errno.h> | ||
#include <float.h> | ||
#include <inttypes.h> | ||
#include <iso646.h> | ||
#include <limits.h> | ||
#include <locale.h> | ||
#include <math.h> | ||
#include <setjmp.h> | ||
#include <signal.h> | ||
#include <stdarg.h> | ||
#include <stddef.h> | ||
#include <stdint.h> | ||
#include <stdio.h> | ||
#include <stdlib.h> | ||
#include <string.h> | ||
#include <time.h> | ||
#include <wchar.h> | ||
#include <wctype.h> | ||
|
||
// Headers deprecated since C++11: expect no diagnostics. | ||
#include <fenv.h> | ||
#include <stdalign.h> | ||
#include <stdbool.h> | ||
#include <tgmath.h> | ||
#include <uchar.h> | ||
|
||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'assert.h'; consider using 'cassert' instead [modernize-deprecated-headers] | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'complex.h'; consider using 'ccomplex' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'ctype.h'; consider using 'cctype' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'errno.h'; consider using 'cerrno' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'float.h'; consider using 'cfloat' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'inttypes.h'; consider using 'cinttypes' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'iso646.h'; consider using 'ciso646' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'limits.h'; consider using 'climits' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'locale.h'; consider using 'clocale' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'math.h'; consider using 'cmath' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'setjmp.h'; consider using 'csetjmp' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'signal.h'; consider using 'csignal' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stdarg.h'; consider using 'cstdarg' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stddef.h'; consider using 'cstddef' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stdint.h'; consider using 'cstdint' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stdio.h'; consider using 'cstdio' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stdlib.h'; consider using 'cstdlib' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'string.h'; consider using 'cstring' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'time.h'; consider using 'ctime' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'wchar.h'; consider using 'cwchar' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'wctype.h'; consider using 'cwctype' instead | ||
|
||
// CHECK-FIXES: #include <cassert> | ||
// CHECK-FIXES: #include <ccomplex> | ||
// CHECK-FIXES: #include <cctype> | ||
// CHECK-FIXES: #include <cerrno> | ||
// CHECK-FIXES: #include <cfloat> | ||
// CHECK-FIXES: #include <cinttypes> | ||
// CHECK-FIXES: #include <ciso646> | ||
// CHECK-FIXES: #include <climits> | ||
// CHECK-FIXES: #include <clocale> | ||
// CHECK-FIXES: #include <cmath> | ||
// CHECK-FIXES: #include <csetjmp> | ||
// CHECK-FIXES: #include <csignal> | ||
// CHECK-FIXES: #include <cstdarg> | ||
// CHECK-FIXES: #include <cstddef> | ||
// CHECK-FIXES: #include <cstdint> | ||
// CHECK-FIXES: #include <cstdio> | ||
// CHECK-FIXES: #include <cstdlib> | ||
// CHECK-FIXES: #include <cstring> | ||
// CHECK-FIXES: #include <ctime> | ||
// CHECK-FIXES: #include <cwchar> | ||
// CHECK-FIXES: #include <cwctype> | ||
|
||
#include "assert.h" | ||
#include "complex.h" | ||
#include "ctype.h" | ||
#include "errno.h" | ||
#include "float.h" | ||
#include "inttypes.h" | ||
#include "iso646.h" | ||
#include "limits.h" | ||
#include "locale.h" | ||
#include "math.h" | ||
#include "setjmp.h" | ||
#include "signal.h" | ||
#include "stdarg.h" | ||
#include "stddef.h" | ||
#include "stdint.h" | ||
#include "stdio.h" | ||
#include "stdlib.h" | ||
#include "string.h" | ||
#include "time.h" | ||
#include "wchar.h" | ||
#include "wctype.h" | ||
|
||
// Headers deprecated since C++11; expect no diagnostics | ||
#include "fenv.h" | ||
#include "stdalign.h" | ||
#include "stdbool.h" | ||
#include "tgmath.h" | ||
#include "uchar.h" | ||
|
||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'assert.h'; consider using 'cassert' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'complex.h'; consider using 'ccomplex' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'ctype.h'; consider using 'cctype' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'errno.h'; consider using 'cerrno' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'float.h'; consider using 'cfloat' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'inttypes.h'; consider using 'cinttypes' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'iso646.h'; consider using 'ciso646' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'limits.h'; consider using 'climits' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'locale.h'; consider using 'clocale' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'math.h'; consider using 'cmath' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'setjmp.h'; consider using 'csetjmp' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'signal.h'; consider using 'csignal' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stdarg.h'; consider using 'cstdarg' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stddef.h'; consider using 'cstddef' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stdint.h'; consider using 'cstdint' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stdio.h'; consider using 'cstdio' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'stdlib.h'; consider using 'cstdlib' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'string.h'; consider using 'cstring' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'time.h'; consider using 'ctime' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'wchar.h'; consider using 'cwchar' instead | ||
// CHECK-MESSAGES: :[[@LINE-29]]:10: warning: inclusion of deprecated C++ header 'wctype.h'; consider using 'cwctype' instead | ||
|
||
// CHECK-FIXES: #include <cassert> | ||
// CHECK-FIXES: #include <ccomplex> | ||
// CHECK-FIXES: #include <cctype> | ||
// CHECK-FIXES: #include <cerrno> | ||
// CHECK-FIXES: #include <cfloat> | ||
// CHECK-FIXES: #include <cinttypes> | ||
// CHECK-FIXES: #include <ciso646> | ||
// CHECK-FIXES: #include <climits> | ||
// CHECK-FIXES: #include <clocale> | ||
// CHECK-FIXES: #include <cmath> | ||
// CHECK-FIXES: #include <csetjmp> | ||
// CHECK-FIXES: #include <csignal> | ||
// CHECK-FIXES: #include <cstdarg> | ||
// CHECK-FIXES: #include <cstddef> | ||
// CHECK-FIXES: #include <cstdint> | ||
// CHECK-FIXES: #include <cstdio> | ||
// CHECK-FIXES: #include <cstdlib> | ||
// CHECK-FIXES: #include <cstring> | ||
// CHECK-FIXES: #include <ctime> | ||
// CHECK-FIXES: #include <cwchar> | ||
// CHECK-FIXES: #include <cwctype> |
Oops, something went wrong.