# Copyright 2018 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.


import re


def compile_fn(api, checkout_root, out_dir):
  skia_dir      = checkout_root.join('skia')
  compiler      = api.vars.builder_cfg.get('compiler')
  configuration = api.vars.builder_cfg.get('configuration')
  extra_tokens  = api.vars.extra_tokens
  os            = api.vars.builder_cfg.get('os')
  target_arch   = api.vars.builder_cfg.get('target_arch')

  assert compiler == 'Clang'  # At this rate we might not ever support GCC.

  extra_cflags = []
  if configuration == 'Debug':
    extra_cflags.append('-O1')

  ndk_asset = 'android_ndk_linux'
  ndk_path = ndk_asset
  if 'Mac' in os:
    ndk_asset = 'android_ndk_darwin'
    ndk_path = ndk_asset
  elif 'Win' in os:
    ndk_asset = 'android_ndk_windows'
    ndk_path = 'n'

  quote = lambda x: '"%s"' % x
  args = {
      'ndk': quote(api.vars.slave_dir.join(ndk_path)),
      'target_cpu': quote(target_arch),
  }
  extra_cflags.append('-DDUMMY_ndk_version=%s' %
                      api.run.asset_version(ndk_asset, skia_dir))

  if configuration != 'Debug':
    args['is_debug'] = 'false'
  if 'Vulkan' in extra_tokens:
    args['ndk_api'] = 24
    args['skia_enable_vulkan_debug_layers'] = 'false'
  if 'ASAN' in extra_tokens:
    args['sanitize'] = '"ASAN"'
    if target_arch == 'arm' and 'ndk_api' not in args:
      args['ndk_api'] = 21

  # If an Android API level is specified, use that.
  for t in extra_tokens:
    m = re.search(r'API(\d+)', t)
    if m and len(m.groups()) == 1:
      args['ndk_api'] = m.groups()[0]
      break

  if extra_cflags:
    args['extra_cflags'] = repr(extra_cflags).replace("'", '"')

  gn_args = ' '.join('%s=%s' % (k,v) for (k,v) in sorted(args.iteritems()))
  gn      = skia_dir.join('bin', 'gn')

  with api.context(cwd=skia_dir):
    api.run(api.python, 'fetch-gn',
            script=skia_dir.join('bin', 'fetch-gn'),
            infra_step=True)

    # If this is the SkQP build, set up the environment and run the script
    # to build the universal APK. This should only run the skqp branches.
    if 'SKQP' in extra_tokens:
      api.infra.update_go_deps()

      output_binary = out_dir.join('run_testlab')
      build_target = skia_dir.join('infra', 'cts', 'run_testlab.go')
      build_cmd = ['go', 'build', '-o', output_binary, build_target]
      with api.context(env=api.infra.go_env):
        api.run(api.step, 'build firebase runner', cmd=build_cmd)

      # Build the APK.
      ndk_asset = 'android_ndk_linux'
      sdk_asset = 'android_sdk_linux'
      android_ndk = api.vars.slave_dir.join(ndk_asset)
      android_home = api.vars.slave_dir.join(sdk_asset, 'android-sdk')
      env = {
        'ANDROID_NDK': android_ndk,
        'ANDROID_HOME': android_home,
        'APK_OUTPUT_DIR': out_dir,
      }

      mk_universal = skia_dir.join('tools', 'skqp', 'make_universal_apk')
      with api.context(env=env):
        api.run(api.step, 'make_universal', cmd=[mk_universal])
    else:
      api.run(api.step, 'gn gen',
              cmd=[gn, 'gen', out_dir, '--args=' + gn_args])
      api.run(api.step, 'ninja', cmd=['ninja', '-k', '0', '-C', out_dir])


def copy_extra_build_products(api, src, dst):
  pass
