#!/usr/bin/env python
# Copyright 2015 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.

"""Tool to roll Chromium into Mojo. See:
https://github.com/domokit/mojo/wiki/Rolling-code-between-chromium-and-mojo#chromium---mojo-updates
"""

import argparse
import glob
import itertools
import os
import subprocess
import sys
import tempfile
import time
import zipfile

import mopy.gn as gn
from mopy.config import Config
from mopy.paths import Paths
from mopy.version import Version

sys.path.append(os.path.join(os.path.dirname(__file__), os.pardir, os.pardir,
                             "third_party", "pyelftools"))
import elftools.elf.elffile as elffile

sys.path.append(os.path.join(os.path.dirname(__file__), os.pardir,
                             'devtools', 'common'))
import android_gdb.signatures as signatures


BLACKLISTED_APPS = [
  # The network service apps are not produced out of the Mojo repo, but may
  # be present in the build dir.
  "network_service.mojo",
  "network_service_apptests.mojo",
]

ARCHITECTURE_INDEPENDENT_FILES = [
  # These are files other than *.mojo files which are part of our binary
  # artifact scheme. These files must be architecture independent.
  "obj/mojo/dart/apptest/apptest.dartzip",
]


def target(config):
  target_name = config.target_os + "-" + config.target_cpu
  if config.is_official_build:
    target_name += "-official"
  return target_name

def find_apps_to_upload(build_dir):
  apps = []
  for path in glob.glob(build_dir + "/*"):
    if not os.path.isfile(path):
      continue
    _, ext = os.path.splitext(path)
    if ext != '.mojo':
      continue
    if os.path.basename(path) in BLACKLISTED_APPS:
      continue
    apps.append(path)
  return apps


def find_architecture_independent_files(build_dir):
  existing_files = []
  for path in ARCHITECTURE_INDEPENDENT_FILES:
    joined_path = os.path.join(build_dir, path)
    if os.path.isfile(joined_path):
      existing_files.append(joined_path)
  return existing_files


def check_call(command_line, dry_run, **kwargs):
  if dry_run:
    print command_line
  else:
    subprocess.check_call(command_line, **kwargs)


def upload(config, source, dest, dry_run, gzip=False):
  paths = Paths(config)
  sys.path.insert(0, os.path.join(paths.src_root, "tools"))
  # pylint: disable=F0401
  import find_depot_tools

  depot_tools_path = find_depot_tools.add_depot_tools_to_path()
  gsutil_exe = os.path.join(depot_tools_path, "third_party", "gsutil", "gsutil")

  command_line = [gsutil_exe, "cp"]
  if gzip and "." in source:
    extension = source.split(".")[-1]
    command_line.extend(["-z", extension])
  command_line.extend([source, dest])

  check_call(command_line, dry_run)


def upload_symbols(config, build_dir, breakpad_upload_urls, dry_run):
  dump_syms_exe = os.path.join(Paths().src_root,
                               "mojo", "tools", "linux64", "dump_syms")
  symupload_exe = os.path.join(Paths().src_root,
                               "mojo", "tools", "linux64", "symupload")
  dest_dir = "gs://mojo/symbols/"
  symbols_dir = os.path.join(build_dir, "symbols")
  with open(os.devnull, "w") as devnull:
    for name in os.listdir(symbols_dir):
      path = os.path.join(symbols_dir, name)
      with open(path) as f:
        signature = signatures.get_signature(f, elffile)
        if signature is not None:
          dest = dest_dir + signature
          upload(config, path, dest, dry_run)
      if breakpad_upload_urls:
        with tempfile.NamedTemporaryFile() as temp:
          check_call([dump_syms_exe, path], dry_run,
                     stdout=temp, stderr=devnull)
          temp.flush()
          for upload_url in breakpad_upload_urls:
            check_call([symupload_exe, temp.name, upload_url], dry_run)

def upload_shell(config, dry_run, verbose):
  paths = Paths(config)
  zipfile_name = target(config)
  version = Version().version

  # Upload the binary.
  # TODO(blundell): Change this to be in the same structure as the LATEST files,
  # e.g., gs://mojo/shell/linux-x64/<version>/shell.zip.
  dest = "gs://mojo/shell/" + version + "/" + zipfile_name + ".zip"
  with tempfile.NamedTemporaryFile() as zip_file:
    with zipfile.ZipFile(zip_file, 'w') as z:
      shell_path = paths.target_mojo_shell_path
      with open(shell_path) as shell_binary:
        shell_filename = os.path.basename(shell_path)
        zipinfo = zipfile.ZipInfo(shell_filename)
        zipinfo.external_attr = 0777 << 16L
        compress_type = zipfile.ZIP_DEFLATED
        if config.target_os == Config.OS_ANDROID:
          # The APK is already compressed.
          compress_type = zipfile.ZIP_STORED
        zipinfo.compress_type = compress_type
        zipinfo.date_time = time.gmtime(os.path.getmtime(shell_path))
        if verbose:
          print "zipping %s" % shell_path
        z.writestr(zipinfo, shell_binary.read())
    upload(config, zip_file.name, dest, dry_run, gzip=False)

  # Update the LATEST file to contain the version of the new binary.
  latest_file = "gs://mojo/shell/%s/LATEST" % target(config)
  write_file_to_gs(version, latest_file, config, dry_run)


def upload_app(app_binary_path, config, dry_run):
  app_binary_name = os.path.basename(app_binary_path)
  version = Version().version
  gsutil_app_location = ("gs://mojo/services/%s/%s/%s" %
                         (target(config), version, app_binary_name))

  # Upload the new binary.
  upload(config, app_binary_path, gsutil_app_location, dry_run)


def upload_file(file_path, config, dry_run):
  file_binary_name = os.path.basename(file_path)
  version = Version().version
  gsutil_file_location = "gs://mojo/file/%s/%s" % (version, file_binary_name)

  # Upload the new binary.
  upload(config, file_path, gsutil_file_location, dry_run)


def write_file_to_gs(file_contents, dest, config, dry_run):
  with tempfile.NamedTemporaryFile() as temp_version_file:
    temp_version_file.write(file_contents)
    temp_version_file.flush()
    upload(config, temp_version_file.name, dest, dry_run)


def main():
  parser = argparse.ArgumentParser(description="Upload binaries for apps and "
      "the Mojo shell to google storage (by default on Linux, but this can be "
      "changed via options).")
  parser.add_argument("-n", "--dry_run", help="Dry run, do not actually "+
      "upload", action="store_true")
  parser.add_argument("-v", "--verbose", help="Verbose mode",
      action="store_true")
  parser.add_argument("--android",
                      action="store_true",
                      help="Upload the shell and apps for Android")
  parser.add_argument("--official",
                      action="store_true",
                      help="Upload the official build of the Android shell")
  parser.add_argument("--symbols-upload-url",
                      action="append", default=[],
                      help="URL of the server to upload breakpad symbols to")
  args = parser.parse_args()

  is_official_build = args.official
  target_os = Config.OS_LINUX
  if args.android:
    target_os = Config.OS_ANDROID
  elif is_official_build:
    print "Uploading official builds is only supported for android."
    return 1

  config = Config(target_os=target_os, is_debug=False,
                  is_official_build=is_official_build)

  upload_shell(config, args.dry_run, args.verbose)

  if is_official_build:
    print "Skipping uploading apps (official apk build)."
    return 0

  build_directory = gn.BuildDirectoryForConfig(config, Paths(config).src_root)
  apps_to_upload = find_apps_to_upload(build_directory)
  for app in apps_to_upload:
    upload_app(app, config, args.dry_run)

  files_to_upload = find_architecture_independent_files(build_directory)
  for file_to_upload in files_to_upload:
    upload_file(file_to_upload, config, args.dry_run)

  upload_symbols(config, build_directory,
                 args.symbols_upload_url, args.dry_run)

  return 0

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