#!/usr/bin/env fuchsia-vendored-python
# Copyright 2020 The Fuchsia 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 to generate runtimes.json for Clang toolchain

This script invokes Clang with different flags to discover the corresponding
runtime paths. The script also ensures that every runtime is stripped and if
not strips it into the .build-id directory, and optionally also generates a
breakpad file. Finally, it prints runtimes.json consumed by the build.
"""

# TODO(phosek): consider rewriting this script in Go reusing the existing logic
# in //tools/debug to populate .build-id directory and generate breakpad.

import argparse
import errno
import json
import os
import re
import shutil
import subprocess
import sys

ELF_MAGIC = b"\x7fELF"

TARGETS = [
    "x86_64-unknown-fuchsia",
    "aarch64-unknown-fuchsia",
    "riscv64-unknown-fuchsia",
]
TRIPLE_TO_TARGET = {
    "x86_64-unknown-fuchsia": "x64",
    "aarch64-unknown-fuchsia": "arm64",
    "riscv64-unknown-fuchsia": "riscv64",
}

# TODO(phosek): use `clang --target=... -print-multi-lib` instead of hardcoding
# these once it supports all variants.
CFLAGS = [
    [],
    ["-fsanitize=address"],
    ["-fsanitize=undefined"],
    ["-fsanitize=hwaddress"],
]
LDFLAGS = [[], ["-static-libstdc++"]]


def trace_link(clang_dir, target, sysroot, cflags, ldflags):
    cmd = [
        os.path.join(clang_dir, "bin", "clang++"),
        "--target=%s" % target,
        "--sysroot=%s" % sysroot,
        "-xc++",
        "-",
        "-o",
        "/dev/null",
        "-Wl,--trace",
    ]
    if cflags:
        cmd.extend(cflags)
    if ldflags:
        cmd.extend(ldflags)
    p = subprocess.Popen(cmd, stdin=subprocess.PIPE, stdout=subprocess.PIPE)
    outs, errs = p.communicate(input=b"int main() {}")
    return outs.decode().splitlines()


def read_soname_and_build_id(readelf, filename):
    p = subprocess.Popen(
        [readelf, "-Wnd", filename], stdout=subprocess.PIPE, env={"LC_ALL": "C"}
    )
    outs, _ = p.communicate()
    if p.returncode != 0:
        raise Exception("failed to read notes")
    match = re.search(
        r"Library soname: \[?([a-zA-Z0-9.+_-]+)\]?", outs.decode()
    )
    soname = match.group(1) if match else None
    match = re.search(r"Build ID: ([a-zA-Z0-9_-]+)", outs.decode())
    if not match:
        raise Exception("build ID missing")
    build_id = match.group(1)
    return soname, build_id


def generate_entry(filename, clang_dir, build_id_dir, dump_syms):
    clang_lib_dir = os.path.join(clang_dir, "lib")

    def rebase_path(path):
        """Rebase a path to clang_lib_dir if it is one of its sub-directories."""
        if path.startswith(clang_lib_dir + os.sep):
            return os.path.relpath(path, clang_lib_dir)
        else:
            return os.path.abspath(path)

    entry = {"dist": rebase_path(filename)}
    soname, build_id = read_soname_and_build_id(
        os.path.join(clang_dir, "bin", "llvm-readelf"), filename
    )
    if soname:
        entry["soname"] = soname
    else:
        soname = os.path.basename(filename)

    # Map a few well-known runtime libraries to their installation name.
    # This is not used at build time, but to generate some build API files.
    # The code below strips the .so and .so.xxx extensions.
    _KNOWN_SO_NAMES = [
        "libc++",
        "libc++abi",
        "libunwind",
    ]
    for known_name in _KNOWN_SO_NAMES:
        if soname == known_name + ".so" or soname.startswith(
            known_name + ".so."
        ):
            entry["name"] = known_name
            break

    if not build_id_dir:
        return entry

    # In many cases, filename will be a symlink to another file.
    # E.g. libc++.so.2 --> libc++.so.2.0.
    real_filename = os.path.realpath(filename)

    dist_file = build_id_dir + "/%s/%s" % (build_id[0:2], build_id[2:])
    debug_file = dist_file + ".debug"
    os.makedirs(os.path.dirname(debug_file), exist_ok=True)
    if not os.path.exists(debug_file):
        try:
            os.link(real_filename, debug_file)
        except OSError as e:
            if e.errno == errno.EXDEV:
                shutil.copyfile(real_filename, debug_file)
            else:
                raise e
    if not os.path.exists(dist_file):
        subprocess.check_call(
            [
                os.path.join(clang_dir, "bin", "llvm-objcopy"),
                "--strip-all",
                debug_file,
                dist_file,
            ]
        )
    entry["dist"] = rebase_path(dist_file)
    entry["debug"] = rebase_path(debug_file)

    if not dump_syms:
        return entry

    breakpad_file = dist_file + ".sym"
    if not os.path.exists(breakpad_file):
        with open(breakpad_file, "w") as f:
            subprocess.check_call(
                [dump_syms, "-r", "-n", soname, "-o", "Fuchsia", debug_file],
                stdout=f,
            )
    entry["breakpad"] = rebase_path(breakpad_file)

    return entry


def main():
    parser = argparse.ArgumentParser()
    parser.add_argument(
        "--clang-prefix", required=True, help="path to Clang toolchain"
    )
    parser.add_argument("--sdk-dir", required=True, help="path to Fuchsia SDK")
    parser.add_argument("--build-id-dir", help="path .build-id directory")
    parser.add_argument(
        "--dump-syms", help="path to Breakpad dump_syms utility"
    )
    args = parser.parse_args()

    clang_dir = os.path.abspath(args.clang_prefix)
    build_id_dir = (
        os.path.abspath(args.build_id_dir) if args.build_id_dir else None
    )

    runtimes = []
    for target in TARGETS:
        arch = TRIPLE_TO_TARGET[target]
        sysroot = os.path.join(args.sdk_dir, "arch", arch, "sysroot")

        for cflags in CFLAGS:
            # HWASan is currently not supported for x64.
            if cflags == ["-fsanitize=hwaddress"] and arch != "arm64":
                continue

            for ldflags in LDFLAGS:
                runtime = []
                for lib in trace_link(
                    clang_dir, target, sysroot, cflags, ldflags
                ):
                    lib_path = os.path.abspath(lib)
                    if not os.path.isfile(lib_path):
                        continue
                    with open(lib_path, "rb") as f:
                        magic = f.read(len(ELF_MAGIC))
                    if magic != ELF_MAGIC:
                        continue
                    if not lib_path.startswith(clang_dir):
                        continue
                    runtime.append(
                        generate_entry(
                            lib_path, clang_dir, build_id_dir, args.dump_syms
                        )
                    )
                runtimes.append(
                    {
                        "cflags": cflags,
                        "ldflags": ldflags,
                        "runtime": runtime,
                        "target": [target],
                    }
                )

    json.dump(runtimes, sys.stdout, indent=2, sort_keys=True)

    return 0


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