# Copyright 2015 The Android Open Source Project
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#      http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

# Functions used to auto-detect and manage the AOSP prebuilts directories
# for other scripts.
#
# Usage:
#
#  1) Call |aosp_dir_register_option| before calling |option_parse| to
#     add the --aosp-dir=<path> option to the current script's command-line.
#
#  2) Call |aosp_dir_parse_option| after calling |option_parse| in order to
#     parse and validate the option or the environment.
#
#     On success, this defines AOSP_DIR and AOSP_PREBUILTS_GCC_DIR

shell_import utils/option_parser.shi

aosp_dir_register_option () {

    OPT_AOSP_DIR=
    option_register_var "--aosp-dir=<dir>" OPT_AOSP_DIR \
            "Specify AOSP root directory. [autodetect]"
}

aosp_dir_parse_option () {
    if [ "$OPT_AOSP_DIR" ]; then
        if [ ! -d "$OPT_AOSP_DIR" ]; then
            panic "Not a directory: $OPT_AOSP_DIR"
        fi
        AOSP_DIR=$OPT_AOSP_DIR
        log "Using AOSP dir: $AOSP_DIR"
    elif [ "$ANDROID_EMULATOR_AOSP_DIR" ]; then
        AOSP_DIR=$ANDROID_EMULATOR_AOSP_DIR
        log "Auto-config: --aosp-dir=$AOSP_DIR  [environment]"
    else
        # Assume that the current script is under external/qemu/android/scripts
        local PROBE_DIR="$(program_directory)/.."
        while [ "$PROBE_DIR" != "/" ]; do
            PROBE_DIR=$(cd "$PROBE_DIR" 2>/dev/null && pwd -P || true)
            if [ -z "$PROBE_DIR" -o "$PROBE_DIR" = "/" ]; then
                dump "Please define ANDROID_EMULATOR_AOSP_DIR in your environment,"
                dump "or use --aosp-dir=<path> on the command-line to specify the"
                dump "root of a valid AOSP source tree."
                panic "Can't find AOSP root."
            fi
            if [ -d "$PROBE_DIR/prebuilts" ]; then
                AOSP_DIR=$PROBE_DIR
                break
            fi
            PROBE_DIR=$PROBE_DIR/..
        done
        log "Auto-config: --aosp-dir=$AOSP_DIR  [auto-detect]"
    fi

    AOSP_DIR=$(cd "$AOSP_DIR" && pwd -P 2>/dev/null)
    AOSP_PREBUILTS_GCC_DIR=$AOSP_DIR/prebuilts/gcc
    AOSP_PREBUILTS_CLANG_DIR=$AOSP_DIR/prebuilts/clang
    if [ ! -d "$AOSP_PREBUILTS_GCC_DIR" ]; then
        panic "Not a valid AOSP tree: missing directory: $AOSP_PREBUILTS_GCC_DIR"
    fi
    if [ ! -d "$AOSP_PREBUILTS_CLANG_DIR" ]; then
        panic "Not a valid AOSP tree: missing directory: $AOSP_PREBUILTS_CLANG_DIR"
    fi
}

# Return the AOSP subdirectory that contains the prebuilt toolchain to be
# used for a given host system.
# $1: System name (e.g. 'linux' or 'linux-x86_64')
aosp_prebuilt_toolchain_subdir_for () {
    case $1 in
        linux*)
            printf "prebuilts/gcc/linux-x86/host/x86_64-linux-glibc2.11-4.8"
            ;;
        darwin*)
            printf "prebuilts/clang/darwin-x86/sdk/3.5"
            ;;
        windows*)
            printf "prebuilts/gcc/linux-x86/host/x86_64-w64-mingw32-4.8"
            ;;
    esac
}

# Return the subdirectory that contains the breakpad prebuilts to be
# used for a given host system.
# $1: System name (e.g. 'linux-x86' or 'linux-x86_64')
aosp_prebuilt_breakpad_subdir_for () {
    printf "prebuilts/android-emulator-build/common/breakpad/$1"
}

# Return the AOSP subdirectory corresponding to the toolchain's sysroot.
# $1: System name (e.g. 'linux-x86' or 'linux-x86_64')
aosp_prebuilt_toolchain_sysroot_subdir_for () {
    local PREBUILT_DIR
    PREBUILT_DIR="$(aosp_prebuilt_toolchain_subdir_for "$1")"
    case $1 in
        linux*)
            printf "${PREBUILT_DIR}/x86_64-linux"
            ;;
        darwin*)
            # We use the developer machine's system SDK.
            printf ""
            ;;
        windows*)
            printf "${PREBUILT_DIR}/x86_64-w64-mingw32"
            ;;
    esac
}

aosp_prebuilt_toolchain_prefix_for () {
    case $1 in
        linux*)
            printf "x86_64-linux-"
            ;;
        darwin*)
            printf ""
            ;;
        windows*)
            printf "x86_64-w64-mingw32-"
            ;;
    esac
}

# Find the AOSP top-level directory, starting from a given sub-directory.
# $1: Starting directory, must be a sub-directory of the AOSP checkout.
# Out: AOSP directory path on success, empty string on failure.
aosp_find_top_dir_from () {
    local PROBE_DIR
    PROBE_DIR=$1
    while true; do
        if [ -z "$PROBE_DIR" -o "$PROBE_DIR" = "/" -o ! -d "$PROBE_DIR" ]; then
            # Could not find anything, weird.
            return
        fi
        # Use prebuilts/qemu-kernel, as the test sub-directory, given that
        # it should be part of all interesting AOSP checkouts (platform and
        # SDK ones).
        if [ -d "$PROBE_DIR"/prebuilts/qemu-kernel ]; then
            printf "%s" "$PROBE_DIR"
            return
        fi
        PROBE_DIR=$(cd "$PROBE_DIR"/.. && pwd -P || true)
    done
}
