clang-tools  8.0.0
AvoidCArraysCheck.cpp
Go to the documentation of this file.
1 //===--- AvoidCArraysCheck.cpp - clang-tidy -------------------------------===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 
10 #include "AvoidCArraysCheck.h"
11 #include "clang/AST/ASTContext.h"
12 #include "clang/ASTMatchers/ASTMatchFinder.h"
13 
14 using namespace clang::ast_matchers;
15 
16 namespace {
17 
18 AST_MATCHER(clang::TypeLoc, hasValidBeginLoc) {
19  return Node.getBeginLoc().isValid();
20 }
21 
22 AST_MATCHER_P(clang::TypeLoc, hasType,
23  clang::ast_matchers::internal::Matcher<clang::Type>,
24  InnerMatcher) {
25  const clang::Type *TypeNode = Node.getTypePtr();
26  return TypeNode != nullptr &&
27  InnerMatcher.matches(*TypeNode, Finder, Builder);
28 }
29 
30 AST_MATCHER(clang::RecordDecl, isExternCContext) {
31  return Node.isExternCContext();
32 }
33 
34 AST_MATCHER(clang::ParmVarDecl, isArgvOfMain) {
35  const clang::DeclContext *DC = Node.getDeclContext();
36  const auto *FD = llvm::dyn_cast<clang::FunctionDecl>(DC);
37  return FD ? FD->isMain() : false;
38 }
39 
40 } // namespace
41 
42 namespace clang {
43 namespace tidy {
44 namespace modernize {
45 
46 void AvoidCArraysCheck::registerMatchers(MatchFinder *Finder) {
47  // std::array<> is avaliable since C++11.
48  if (!getLangOpts().CPlusPlus11)
49  return;
50 
51  Finder->addMatcher(
52  typeLoc(hasValidBeginLoc(), hasType(arrayType()),
53  unless(anyOf(hasParent(parmVarDecl(isArgvOfMain())),
54  hasParent(varDecl(isExternC())),
55  hasParent(fieldDecl(
56  hasParent(recordDecl(isExternCContext())))),
57  hasAncestor(functionDecl(isExternC())))))
58  .bind("typeloc"),
59  this);
60 }
61 
62 void AvoidCArraysCheck::check(const MatchFinder::MatchResult &Result) {
63  const auto *ArrayType = Result.Nodes.getNodeAs<TypeLoc>("typeloc");
64 
65  static constexpr llvm::StringLiteral UseArray = llvm::StringLiteral(
66  "do not declare C-style arrays, use std::array<> instead");
67  static constexpr llvm::StringLiteral UseVector = llvm::StringLiteral(
68  "do not declare C VLA arrays, use std::vector<> instead");
69 
70  diag(ArrayType->getBeginLoc(),
71  ArrayType->getTypePtr()->isVariableArrayType() ? UseVector : UseArray);
72 }
73 
74 } // namespace modernize
75 } // namespace tidy
76 } // namespace clang
AST_MATCHER(BinaryOperator, isAssignmentOperator)
Definition: Matchers.h:20
llvm::Optional< llvm::Expected< tooling::AtomicChanges > > Result
===– Representation.cpp - ClangDoc Representation --------—*- C++ -*-===//
AST_MATCHER_P(FunctionDecl, throws, internal::Matcher< Type >, InnerMatcher)