// Copyright (c) 2017, the R8 project authors. Please see the AUTHORS file
// for details. All rights reserved. Use of this source code is governed by a
// BSD-style license that can be found in the LICENSE file.
package com.android.tools.r8;

import com.android.tools.r8.errors.CompilationError;
import com.android.tools.r8.origin.Origin;
import com.android.tools.r8.origin.PathOrigin;
import com.android.tools.r8.utils.Pair;
import com.google.common.collect.ImmutableList;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.List;
import java.util.function.BiConsumer;

/** Immutable command structure for an invocation of the {@link ExtractMarker} tool. */
@Keep
public class ExtractMarkerCommand {

  /** Builder for constructing a {@link ExtractMarkerCommand}. */
  @Keep
  public static class Builder {
    private boolean printHelp = false;
    private final List<Path> programFiles = new ArrayList<>();
    private final List<Pair<Origin, byte[]>> dexData = new ArrayList<>();
    private final List<Pair<Origin, byte[]>> cfData = new ArrayList<>();
    private MarkerInfoConsumer consumer;
    private DiagnosticsHandler handler;

    Builder(DiagnosticsHandler handler) {
      this.handler = handler;
    }

    public Builder setPrintHelp(boolean printHelp) {
      this.printHelp = printHelp;
      return this;
    }

    public boolean isPrintHelp() {
      return printHelp;
    }

    /**
     * Add program files to extract marker information from.
     *
     * <p>All program files supported by the input and output of D8/R8 can be passed here.
     */
    public Builder addProgramFiles(Path... programFiles) {
      return addProgramFiles(Arrays.asList(programFiles));
    }

    /**
     * Add program files to extract marker information from.
     *
     * <p>All program files supported by the input and output of D8/R8 can be passed here.
     */
    public Builder addProgramFiles(Collection<Path> programFiles) {
      this.programFiles.addAll(programFiles);
      return this;
    }

    /** Add dex encoded bytes to extract marker information from. */
    public Builder addDexProgramData(byte[] data, Origin origin) {
      dexData.add(new Pair<>(origin, data));
      return this;
    }

    /** Add classfile encoded bytes to extract marker information from. */
    public Builder addClassProgramData(byte[] data, Origin origin) {
      cfData.add(new Pair<>(origin, data));
      return this;
    }

    /** Set the callback to obtain the collected marker information. */
    public Builder setMarkerInfoConsumer(MarkerInfoConsumer consumer) {
      this.consumer = consumer;
      return this;
    }

    public ExtractMarkerCommand build() {
      // If printing versions ignore everything else.
      if (isPrintHelp()) {
        return new ExtractMarkerCommand(isPrintHelp());
      }
      return new ExtractMarkerCommand(handler, consumer, programFiles, dexData, cfData);
    }
  }

  static final String USAGE_MESSAGE =
      String.join(
          "\n",
          ImmutableList.of(
              "Usage: extractmarker [options] <input-files>",
              " where <input-files> are D8 supported input/output files and options are:",
              "  --help                  # Print this message."));

  public static Builder builder() {
    return builder(new DiagnosticsHandler() {});
  }

  public static Builder builder(DiagnosticsHandler handler) {
    return new Builder(handler);
  }

  public static Builder parse(String[] args) {
    Builder builder = builder();
    parse(args, builder);
    return builder;
  }

  private static void parse(String[] args, Builder builder) {
    for (int i = 0; i < args.length; i++) {
      String arg = args[i].trim();
      if (arg.equals("--help")) {
        builder.setPrintHelp(true);
      } else {
        if (arg.startsWith("--")) {
          throw new CompilationError("Unknown option: " + arg);
        }
        builder.addProgramFiles(Paths.get(arg));
      }
    }
  }

  private final boolean printHelp;
  private final DiagnosticsHandler handler;
  private final MarkerInfoConsumer consumer;
  private final List<Path> programFiles;
  private final List<Pair<Origin, byte[]>> dexData;
  private final List<Pair<Origin, byte[]>> cfData;

  private ExtractMarkerCommand(
      DiagnosticsHandler handler,
      MarkerInfoConsumer consumer,
      List<Path> programFiles,
      List<Pair<Origin, byte[]>> dexData,
      List<Pair<Origin, byte[]>> cfData) {
    this.printHelp = false;
    this.handler = handler;
    this.consumer = consumer;
    this.programFiles = programFiles;
    this.dexData = dexData;
    this.cfData = cfData;
  }

  private ExtractMarkerCommand(boolean printHelp) {
    this.printHelp = printHelp;
    handler = null;
    consumer = null;
    programFiles = null;
    dexData = null;
    cfData = null;
  }

  public boolean isPrintHelp() {
    return printHelp;
  }

  public MarkerInfoConsumer getMarkerInfoConsumer() {
    return consumer;
  }

  public DiagnosticsHandler getDiagnosticsHandler() {
    return handler;
  }

  public void forEachEntry(
      BiConsumer<Path, Origin> onProgramFile,
      BiConsumer<byte[], Origin> onDexData,
      BiConsumer<byte[], Origin> onCfData) {
    programFiles.forEach(path -> onProgramFile.accept(path, new PathOrigin(path)));
    dexData.forEach(pair -> onDexData.accept(pair.getSecond(), pair.getFirst()));
    cfData.forEach(pair -> onCfData.accept(pair.getSecond(), pair.getFirst()));
  }
}
