#!/usr/bin/env python
# Copyright 2019 The Chromium Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.
r"""Automatically fetch, build, and run clang-tidy from source.

This script seeks to automate the steps detailed in docs/clang_tidy.md.

Example: the following command disables clang-tidy's default checks (-*) and
enables the clang static analyzer checks.

    tools/clang/scripts/clang_tidy_tool.py \\
       --checks='-*,clang-analyzer-*,-clang-analyzer-alpha*' \\
       --header-filter='.*' \\
       out/Release chrome

The same, but checks the changes only.

    git diff -U5 | tools/clang/scripts/clang_tidy_tool.py \\
       --diff \\
       --checks='-*,clang-analyzer-*,-clang-analyzer-alpha*' \\
       --header-filter='.*' \\
       out/Release chrome
"""

from __future__ import print_function

import argparse
import os
import subprocess
import sys
import update

import build_clang_tools_extra


def GetBinaryPath(build_dir, binary):
  if sys.platform == 'win32':
    binary += '.exe'
  return os.path.join(build_dir, 'bin', binary)


def BuildNinjaTarget(out_dir, ninja_target):
  args = ['autoninja', '-C', out_dir, ninja_target]
  subprocess.check_call(args, shell=sys.platform == 'win32')


def GenerateCompDb(out_dir):
  gen_compdb_script = os.path.join(
      os.path.dirname(__file__), 'generate_compdb.py')
  comp_db_file_path = os.path.join(out_dir, 'compile_commands.json')
  args = [
      sys.executable,
      gen_compdb_script,
      '-p',
      out_dir,
      '-o',
      comp_db_file_path,
  ]
  subprocess.check_call(args)

  # The resulting CompDb file includes /showIncludes which causes clang-tidy to
  # output a lot of unnecessary text to the console.
  with open(comp_db_file_path, 'r') as comp_db_file:
    comp_db_data = comp_db_file.read();

  # The trailing space on /showIncludes helps keep single-spaced flags.
  comp_db_data = comp_db_data.replace('/showIncludes ', '')

  with open(comp_db_file_path, 'w') as comp_db_file:
    comp_db_file.write(comp_db_data)


def RunClangTidy(checks, header_filter, auto_fix, clang_src_dir,
                 clang_build_dir, out_dir, ninja_target):
  """Invoke the |run-clang-tidy.py| script."""
  run_clang_tidy_script = os.path.join(
      clang_src_dir, 'clang-tools-extra', 'clang-tidy', 'tool',
      'run-clang-tidy.py')

  clang_tidy_binary = GetBinaryPath(clang_build_dir, 'clang-tidy')
  clang_apply_rep_binary = GetBinaryPath(clang_build_dir,
                                         'clang-apply-replacements')

  args = [
      sys.executable,
      run_clang_tidy_script,
      '-quiet',
      '-p',
      out_dir,
      '-clang-tidy-binary',
      clang_tidy_binary,
      '-clang-apply-replacements-binary',
      clang_apply_rep_binary,
  ]

  if checks:
    args.append('-checks={}'.format(checks))

  if header_filter:
    args.append('-header-filter={}'.format(header_filter))

  if auto_fix:
    args.append('-fix')

  args.append(ninja_target)
  subprocess.check_call(args)


def RunClangTidyDiff(checks, auto_fix, clang_src_dir, clang_build_dir, out_dir):
  """Invoke the |clang-tidy-diff.py| script over the diff from stdin."""
  clang_tidy_diff_script = os.path.join(
      clang_src_dir, 'clang-tools-extra', 'clang-tidy', 'tool',
      'clang-tidy-diff.py')

  clang_tidy_binary = GetBinaryPath(clang_build_dir, 'clang-tidy')

  args = [
      clang_tidy_diff_script,
      '-quiet',
      '-p1',
      '-path',
      out_dir,
      '-clang-tidy-binary',
      clang_tidy_binary,
  ]

  if checks:
    args.append('-checks={}'.format(checks))

  if auto_fix:
    args.append('-fix')

  subprocess.check_call(args)


def main():
  script_name = sys.argv[0]

  parser = argparse.ArgumentParser(
      formatter_class=argparse.RawDescriptionHelpFormatter, epilog=__doc__)
  parser.add_argument(
      '--fetch',
      nargs='?',
      const=update.CLANG_REVISION,
      help='Fetch and build clang sources')
  parser.add_argument(
      '--build',
      action='store_true',
      help='build clang sources to get clang-tidy')
  parser.add_argument(
      '--diff',
      action='store_true',
      default=False,
      help ='read diff from the stdin and check it')
  parser.add_argument('--clang-src-dir', type=str,
                      help='override llvm and clang checkout location')
  parser.add_argument('--clang-build-dir', type=str,
                      help='override clang build dir location')
  parser.add_argument('--checks', help='passed to clang-tidy')
  parser.add_argument('--header-filter', help='passed to clang-tidy')
  parser.add_argument(
      '--auto-fix',
      action='store_true',
      help='tell clang-tidy to auto-fix errors')
  parser.add_argument('OUT_DIR', help='where we are building Chrome')
  parser.add_argument('NINJA_TARGET', help='ninja target')
  args = parser.parse_args()

  steps = []

  # If the user hasn't provided a clang checkout and build dir, checkout and
  # build clang-tidy where update.py would.
  if not args.clang_src_dir:
    args.clang_src_dir = build_clang_tools_extra.GetCheckoutDir(args.OUT_DIR)
  if not args.clang_build_dir:
    args.clang_build_dir = build_clang_tools_extra.GetBuildDir(args.OUT_DIR)
  elif (args.clang_build_dir and not
        os.path.isfile(GetBinaryPath(args.clang_build_dir, 'clang-tidy'))):
    sys.exit('clang-tidy binary doesn\'t exist at ' +
             GetBinaryPath(args.clang_build_dir, 'clang-tidy'))

  if args.fetch:
    steps.append(('Fetching LLVM sources', lambda:
                  build_clang_tools_extra.FetchLLVM(args.clang_src_dir,
                                                    args.fetch)))

  if args.build:
    steps.append(('Building clang-tidy',
                  lambda: build_clang_tools_extra.BuildTargets(
                      args.clang_build_dir,
                      ['clang-tidy', 'clang-apply-replacements'])))

  steps += [
      ('Building ninja target: %s' % args.NINJA_TARGET,
      lambda: BuildNinjaTarget(args.OUT_DIR, args.NINJA_TARGET)),
      ('Generating compilation DB', lambda: GenerateCompDb(args.OUT_DIR))
    ]
  if args.diff:
    steps += [
        ('Running clang-tidy on diff', lambda: RunClangTidyDiff(
            args.checks, args.auto_fix, args.clang_src_dir, args.
            clang_build_dir, args.OUT_DIR)),
    ]
  else:
    steps += [
        ('Running clang-tidy',
        lambda: RunClangTidy(args.checks, args.header_filter,
                             args.auto_fix, args.clang_src_dir,
                             args.clang_build_dir, args.OUT_DIR,
                             args.NINJA_TARGET)),
    ]

  # Run the steps in sequence.
  for i, (msg, step_func) in enumerate(steps):
    # Print progress message
    print('-- %s %s' % (script_name, '-' * (80 - len(script_name) - 4)))
    print('-- [%d/%d] %s' % (i + 1, len(steps), msg))
    print(80 * '-')

    step_func()

  return 0


if __name__ == '__main__':
  sys.exit(main())
