//===--- MultipleStatementMacroCheck.cpp - clang-tidy----------------------===//
//
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
// See https://llvm.org/LICENSE.txt for license information.
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
//
//===----------------------------------------------------------------------===//

#include "MultipleStatementMacroCheck.h"
#include "clang/AST/ASTContext.h"
#include "clang/ASTMatchers/ASTMatchFinder.h"

using namespace clang::ast_matchers;

namespace clang {
namespace tidy {
namespace bugprone {

namespace {

AST_MATCHER(Expr, isInMacro) { return Node.getBeginLoc().isMacroID(); }

/// Find the next statement after `S`.
const Stmt *nextStmt(const MatchFinder::MatchResult &Result, const Stmt *S) {
  auto Parents = Result.Context->getParents(*S);
  if (Parents.empty())
    return nullptr;
  const auto *Parent = Parents[0].get<Stmt>();
  if (!Parent)
    return nullptr;
  const Stmt *Prev = nullptr;
  for (const Stmt *Child : Parent->children()) {
    if (Prev == S)
      return Child;
    Prev = Child;
  }
  return nextStmt(Result, Parent);
}

using ExpansionRanges = std::vector<SourceRange>;

/// \bried Get all the macro expansion ranges related to `Loc`.
///
/// The result is ordered from most inner to most outer.
ExpansionRanges getExpansionRanges(SourceLocation Loc,
                                   const MatchFinder::MatchResult &Result) {
  ExpansionRanges Locs;
  while (Loc.isMacroID()) {
    Locs.push_back(
        Result.SourceManager->getImmediateExpansionRange(Loc).getAsRange());
    Loc = Locs.back().getBegin();
  }
  return Locs;
}

} // namespace

void MultipleStatementMacroCheck::registerMatchers(MatchFinder *Finder) {
  const auto Inner = expr(isInMacro(), unless(compoundStmt())).bind("inner");
  Finder->addMatcher(
      stmt(anyOf(ifStmt(hasThen(Inner)), ifStmt(hasElse(Inner)).bind("else"),
                 whileStmt(hasBody(Inner)), forStmt(hasBody(Inner))))
          .bind("outer"),
      this);
}

void MultipleStatementMacroCheck::check(
    const MatchFinder::MatchResult &Result) {
  const auto *Inner = Result.Nodes.getNodeAs<Expr>("inner");
  const auto *Outer = Result.Nodes.getNodeAs<Stmt>("outer");
  const auto *Next = nextStmt(Result, Outer);
  if (!Next)
    return;

  SourceLocation OuterLoc = Outer->getBeginLoc();
  if (Result.Nodes.getNodeAs<Stmt>("else"))
    OuterLoc = cast<IfStmt>(Outer)->getElseLoc();

  auto InnerRanges = getExpansionRanges(Inner->getBeginLoc(), Result);
  auto OuterRanges = getExpansionRanges(OuterLoc, Result);
  auto NextRanges = getExpansionRanges(Next->getBeginLoc(), Result);

  // Remove all the common ranges, starting from the top (the last ones in the
  // list).
  while (!InnerRanges.empty() && !OuterRanges.empty() && !NextRanges.empty() &&
         InnerRanges.back() == OuterRanges.back() &&
         InnerRanges.back() == NextRanges.back()) {
    InnerRanges.pop_back();
    OuterRanges.pop_back();
    NextRanges.pop_back();
  }

  // Inner and Next must have at least one more macro that Outer doesn't have,
  // and that range must be common to both.
  if (InnerRanges.empty() || NextRanges.empty() ||
      InnerRanges.back() != NextRanges.back())
    return;

  diag(InnerRanges.back().getBegin(), "multiple statement macro used without "
                                      "braces; some statements will be "
                                      "unconditionally executed");
}

} // namespace bugprone
} // namespace tidy
} // namespace clang
