# Copyright (c) 2012 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""Script for calculating compatible binhosts.

Generates a file that sets the specified board's binhosts to include all of the
other compatible boards in this buildroot.
"""

from __future__ import print_function

import collections
import glob
import optparse  # pylint: disable=deprecated-module
import os
import sys

from chromite.lib import cros_build_lib


def FindCandidateBoards():
  """Find candidate local boards to grab prebuilts from."""
  portageq_prefix = "/usr/local/bin/portageq-"
  for path in sorted(glob.glob("%s*" % portageq_prefix)):
    # Strip off the portageq prefix, leaving only the board.
    yield path.replace(portageq_prefix, "")


def SummarizeCompatibility(board):
  """Returns a string that will be the same for compatible boards."""
  cmd = ["portageq-%s" % board, "envvar", "ARCH", "CFLAGS"]
  summary = cros_build_lib.RunCommand(cmd, redirect_stdout=True,
                                      print_cmd=False).output.rstrip()
  # We will add -clang-syntax to falco and nyan board. So we need to
  # filter out -clang-syntax to make the flags from PFQ are the same as
  # the release-board. See crbug.com/499115
  # TODO(yunlian): Remove this when all the boards are build with -clang-syntax
  return summary.replace(" -clang-syntax", "")


def GenerateBinhostLine(build_root, compatible_boards):
  """Generate a binhost line pulling binaries from the specified boards."""
  # TODO(davidjames): Prioritize binhosts with more matching use flags.
  local_binhosts = " ".join([
      "file://localhost" + os.path.join(build_root, x, "packages")
      for x in sorted(compatible_boards)])
  return "LOCAL_BINHOST='%s'" % local_binhosts


def main(argv):
  parser = optparse.OptionParser(usage="USAGE: ./%prog --board=board [options]")

  parser.add_option("--build_root", default="/build",
                    dest="build_root",
                    help="Location of boards (normally /build)")
  parser.add_option("--board", default=None,
                    dest="board",
                    help="Board name (required).")

  flags, remaining_arguments = parser.parse_args(argv)

  if remaining_arguments or not flags.board:
    parser.print_help()
    sys.exit(1)

  by_compatibility = collections.defaultdict(set)
  compatible_boards = None
  for other_board in FindCandidateBoards():
    compat_id = SummarizeCompatibility(other_board)
    if other_board == flags.board:
      compatible_boards = by_compatibility[compat_id]
    else:
      by_compatibility[compat_id].add(other_board)

  if compatible_boards is None:
    print('Missing portageq wrapper for %s' % flags.board, file=sys.stderr)
    sys.exit(1)

  print('# Generated by cros_generate_local_binhosts.')
  print(GenerateBinhostLine(flags.build_root, compatible_boards))
