// 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.naming;

import com.android.tools.r8.graph.DexField;
import com.android.tools.r8.graph.DexMethod;
import com.android.tools.r8.graph.DexType;
import com.android.tools.r8.naming.ClassNamingForNameMapper.MappedRange;
import com.android.tools.r8.naming.MemberNaming.FieldSignature;
import com.android.tools.r8.naming.MemberNaming.MethodSignature;
import com.android.tools.r8.naming.MemberNaming.Signature;
import com.android.tools.r8.naming.MemberNaming.Signature.SignatureKind;
import com.android.tools.r8.naming.mappinginformation.MappingInformation;
import com.android.tools.r8.position.Position;
import com.android.tools.r8.utils.Reporter;
import com.android.tools.r8.utils.ThrowingConsumer;
import com.google.common.base.Objects;
import com.google.common.collect.ImmutableMap;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.Collection;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.function.Consumer;

/**
 * Stores name information for a class.
 * <p>
 * The main differences of this against {@link ClassNamingForNameMapper} are:
 *   1) field and method mappings are maintained and searched separately for faster lookup;
 *   2) similar to the relation between {@link ClassNameMapper} and {@link SeedMapper}, this one
 *   uses original {@link Signature} as a key to look up {@link MemberNaming},
 *   whereas {@link ClassNamingForNameMapper} uses renamed {@link Signature} as a key; and thus
 *   3) logic of {@link #lookup} and {@link #lookupByOriginalSignature} are inverted; and
 *   4) {@link #lookupByOriginalItem}'s are introduced for lightweight lookup.
 */
public class ClassNamingForMapApplier implements ClassNaming {

  public static class Builder extends ClassNaming.Builder {

    private final String originalName;
    private final String renamedName;
    private final Position position;
    private final Reporter reporter;
    private final Map<MethodSignature, List<MemberNaming>> qualifiedMethodMembers = new HashMap<>();
    private final Map<MethodSignature, MemberNaming> methodMembers = new HashMap<>();
    private final Map<FieldSignature, MemberNaming> fieldMembers = new HashMap<>();

    private Builder(String renamedName, String originalName, Position position, Reporter reporter) {
      this.originalName = originalName;
      this.renamedName = renamedName;
      this.position = position;
      this.reporter = reporter;
    }

    @Override
    public ClassNaming.Builder addMemberEntry(MemberNaming entry) {
      // Unlike {@link ClassNamingForNameMapper.Builder#addMemberEntry},
      // the key is original signature.
      if (entry.isMethodNaming()) {
        MethodSignature signature = entry.getOriginalSignature().asMethodSignature();
        if (signature.isQualified()) {
          qualifiedMethodMembers.computeIfAbsent(signature, k -> new ArrayList<>(2)).add(entry);
        } else if (methodMembers.put(signature, entry) != null) {
          reporter.error(
              ProguardMapError.duplicateSourceMember(
                  signature.toString(), this.originalName, entry.getPosition()));
        }
      } else {
        FieldSignature signature = entry.getOriginalSignature().asFieldSignature();
        if (!signature.isQualified() && fieldMembers.put(signature, entry) != null) {
          reporter.error(
              ProguardMapError.duplicateSourceMember(
                  signature.toString(), this.originalName, entry.getPosition()));
        }
      }
      return this;
    }

    @Override
    public ClassNamingForMapApplier build() {
      return new ClassNamingForMapApplier(
          renamedName, originalName, position, qualifiedMethodMembers, methodMembers, fieldMembers);
    }

    @Override
    public MappedRange addMappedRange(
        Range minifiedRange,
        MemberNaming.MethodSignature originalSignature,
        Range originalRange,
        String renamedName) {
      return null;
    }

    @Override
    public void addMappingInformation(
        MappingInformation info, Consumer<MappingInformation> onProhibitedAddition) {
      // Intentionally empty.
    }
  }

  static Builder builder(
      String renamedName, String originalName, Position position, Reporter reporter) {
    return new Builder(renamedName, originalName, position, reporter);
  }

  private final String originalName;
  final String renamedName;
  final Position position;

  private final ImmutableMap<MethodSignature, List<MemberNaming>> qualifiedMethodMembers;
  private final ImmutableMap<MethodSignature, MemberNaming> methodMembers;
  private final ImmutableMap<FieldSignature, MemberNaming> fieldMembers;

  // Constructor to help chaining {@link ClassNamingForMapApplier} according to class hierarchy.
  ClassNamingForMapApplier(ClassNamingForMapApplier proxy) {
    this(
        proxy.renamedName,
        proxy.originalName,
        proxy.position,
        proxy.qualifiedMethodMembers,
        proxy.methodMembers,
        proxy.fieldMembers);
  }

  private ClassNamingForMapApplier(
      String renamedName,
      String originalName,
      Position position,
      Map<MethodSignature, List<MemberNaming>> qualifiedMethodMembers,
      Map<MethodSignature, MemberNaming> methodMembers,
      Map<FieldSignature, MemberNaming> fieldMembers) {
    this.renamedName = renamedName;
    this.originalName = originalName;
    this.position = position;
    this.qualifiedMethodMembers = ImmutableMap.copyOf(qualifiedMethodMembers);
    this.methodMembers = ImmutableMap.copyOf(methodMembers);
    this.fieldMembers = ImmutableMap.copyOf(fieldMembers);
  }

  public ImmutableMap<MethodSignature, List<MemberNaming>> getQualifiedMethodMembers() {
    return qualifiedMethodMembers;
  }

  @Override
  public <T extends Throwable> void forAllMemberNaming(
      ThrowingConsumer<MemberNaming, T> consumer) throws T {
    forAllFieldNaming(consumer);
    forAllMethodNaming(consumer);
  }

  @Override
  public <T extends Throwable> void forAllFieldNaming(
      ThrowingConsumer<MemberNaming, T> consumer) throws T {
    for (MemberNaming naming : fieldMembers.values()) {
      consumer.accept(naming);
    }
  }

  @Override
  public <T extends Throwable> void forAllMethodNaming(
      ThrowingConsumer<MemberNaming, T> consumer) throws T {
    for (MemberNaming naming : methodMembers.values()) {
      consumer.accept(naming);
    }
  }

  @Override
  public MemberNaming lookup(Signature renamedSignature) {
    // As the key is inverted, this looks a lot like
    //   {@link ClassNamingForNameMapper#lookupByOriginalSignature}.
    Collection<MemberNaming> memberNamings =
        renamedSignature.kind() == SignatureKind.METHOD
            ? methodMembers.values()
            : fieldMembers.values();
    for (MemberNaming memberNaming : memberNamings) {
      if (memberNaming.getResidualSignature().equals(renamedSignature)) {
        return memberNaming;
      }
    }
    return null;
  }

  @Override
  public MemberNaming lookupByOriginalSignature(Signature original) {
    // As the key is inverted, this looks a lot like {@link ClassNamingForNameMapper#lookup}.
    if (original.kind() == SignatureKind.METHOD) {
      return methodMembers.get(original.asMethodSignature());
    } else {
      assert original.kind() == SignatureKind.FIELD;
      return fieldMembers.get(original.asFieldSignature());
    }
  }

  MemberNaming lookupByOriginalItem(DexField field) {
    for (Map.Entry<FieldSignature, MemberNaming> entry : fieldMembers.entrySet()) {
      FieldSignature signature = entry.getKey();
      if (signature.name.equals(field.name.toSourceString())
          && signature.type.equals(field.type.toSourceString())) {
        return entry.getValue();
      }
    }
    return null;
  }

  protected MemberNaming lookupByOriginalItem(DexMethod method) {
    for (Map.Entry<MethodSignature, MemberNaming> entry : methodMembers.entrySet()) {
      MethodSignature signature = entry.getKey();
      if (signature.name.equals(method.name.toSourceString())
          && signature.type.equals(method.proto.returnType.toSourceString())
          && Arrays.equals(signature.parameters,
              Arrays.stream(method.proto.parameters.values)
                  .map(DexType::toSourceString).toArray(String[]::new))) {
        return entry.getValue();
      }
    }
    return null;
  }

  @Override
  public boolean equals(Object o) {
    if (this == o) {
      return true;
    }
    if (!(o instanceof ClassNamingForMapApplier)) {
      return false;
    }

    ClassNamingForMapApplier that = (ClassNamingForMapApplier) o;

    return originalName.equals(that.originalName)
        && renamedName.equals(that.renamedName)
        && qualifiedMethodMembers.equals(that.qualifiedMethodMembers)
        && methodMembers.equals(that.methodMembers)
        && fieldMembers.equals(that.fieldMembers);
  }

  @Override
  public int hashCode() {
    return Objects.hashCode(
        originalName, renamedName, qualifiedMethodMembers, methodMembers, fieldMembers);
  }
}
