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

import com.android.tools.r8.utils.StringUtils;
import com.google.common.collect.ImmutableList;
import java.util.LinkedList;
import java.util.List;
import java.util.Objects;

public abstract class ProguardClassSpecification {

  public static class Builder {

    protected ProguardTypeMatcher classAnnotation;
    protected ProguardAccessFlags classAccessFlags = new ProguardAccessFlags();
    protected ProguardAccessFlags negatedClassAccessFlags = new ProguardAccessFlags();
    protected boolean classTypeNegated = false;
    protected ProguardClassType classType = ProguardClassType.UNSPECIFIED;
    protected ProguardClassNameList classNames;
    protected ProguardTypeMatcher inheritanceAnnotation;
    protected ProguardTypeMatcher inheritanceClassName;
    protected boolean inheritanceIsExtends = false;
    protected List<ProguardMemberRule> memberRules = new LinkedList<>();

    protected Builder() {
    }

    public List<ProguardMemberRule> getMemberRules() {
      return memberRules;
    }

    public void setMemberRules(List<ProguardMemberRule> memberRules) {
      this.memberRules = memberRules;
    }

    public boolean getInheritanceIsExtends() {
      return inheritanceIsExtends;
    }

    public void setInheritanceIsExtends(boolean inheritanceIsExtends) {
      this.inheritanceIsExtends = inheritanceIsExtends;
    }

    public boolean hasInheritanceClassName() {
      return inheritanceClassName != null;
    }

    public ProguardTypeMatcher getInheritanceClassName() {
      return inheritanceClassName;
    }

    public void setInheritanceClassName(ProguardTypeMatcher inheritanceClassName) {
      this.inheritanceClassName = inheritanceClassName;
    }

    public ProguardTypeMatcher getInheritanceAnnotation() {
      return inheritanceAnnotation;
    }

    public void setInheritanceAnnotation(ProguardTypeMatcher inheritanceAnnotation) {
      this.inheritanceAnnotation = inheritanceAnnotation;
    }

    public ProguardClassNameList getClassNames() {
      return classNames;
    }

    public void setClassNames(ProguardClassNameList classNames) {
      this.classNames = classNames;
    }

    public ProguardClassType getClassType() {
      return classType;
    }

    public void setClassType(ProguardClassType classType) {
      this.classType = classType;
    }

    public boolean getClassTypeNegated() {
      return classTypeNegated;
    }

    public void setClassTypeNegated(boolean classTypeNegated) {
      this.classTypeNegated = classTypeNegated;
    }

    public ProguardAccessFlags getClassAccessFlags() {
      return classAccessFlags;
    }

    public void setClassAccessFlags(ProguardAccessFlags flags) {
      classAccessFlags = flags;
    }

    public ProguardAccessFlags getNegatedClassAccessFlags() {
      return negatedClassAccessFlags;
    }

    public void setNegatedClassAccessFlags(ProguardAccessFlags flags) {
      negatedClassAccessFlags = flags;
    }

    public ProguardTypeMatcher getClassAnnotation() {
      return classAnnotation;
    }

    public void setClassAnnotation(ProguardTypeMatcher classAnnotation) {
      this.classAnnotation = classAnnotation;
    }

    protected void matchAllSpecification() {
      setClassNames(ProguardClassNameList.singletonList(ProguardTypeMatcher.defaultAllMatcher()));
      setMemberRules(ImmutableList.of(ProguardMemberRule.defaultKeepAllRule()));
    }
  }

  private final ProguardTypeMatcher classAnnotation;
  private final ProguardAccessFlags classAccessFlags;
  private final ProguardAccessFlags negatedClassAccessFlags;
  private final boolean classTypeNegated;
  private final ProguardClassType classType;
  private final ProguardClassNameList classNames;
  private final ProguardTypeMatcher inheritanceAnnotation;
  private final ProguardTypeMatcher inheritanceClassName;
  private final boolean inheritanceIsExtends;
  private final List<ProguardMemberRule> memberRules;

  protected ProguardClassSpecification(
      ProguardTypeMatcher classAnnotation,
      ProguardAccessFlags classAccessFlags,
      ProguardAccessFlags negatedClassAccessFlags,
      boolean classTypeNegated,
      ProguardClassType classType,
      ProguardClassNameList classNames,
      ProguardTypeMatcher inheritanceAnnotation,
      ProguardTypeMatcher inheritanceClassName,
      boolean inheritanceIsExtends,
      List<ProguardMemberRule> memberRules) {
    this.classAnnotation = classAnnotation;
    this.classAccessFlags = classAccessFlags;
    this.negatedClassAccessFlags = negatedClassAccessFlags;
    this.classTypeNegated = classTypeNegated;
    this.classType = classType;
    assert classType != null;
    this.classNames = classNames;
    this.inheritanceAnnotation = inheritanceAnnotation;
    this.inheritanceClassName = inheritanceClassName;
    this.inheritanceIsExtends = inheritanceIsExtends;
    this.memberRules = memberRules;
  }

  public List<ProguardMemberRule> getMemberRules() {
    return memberRules;
  }

  public boolean getInheritanceIsExtends() {
    return inheritanceIsExtends;
  }

  public boolean hasInheritanceClassName() {
    return inheritanceClassName != null;
  }

  public ProguardTypeMatcher getInheritanceClassName() {
    return inheritanceClassName;
  }

  public ProguardTypeMatcher getInheritanceAnnotation() {
    return inheritanceAnnotation;
  }

  public ProguardClassNameList getClassNames() {
    return classNames;
  }

  public ProguardClassType getClassType() {
    return classType;
  }

  public boolean getClassTypeNegated() {
    return classTypeNegated;
  }

  public ProguardAccessFlags getClassAccessFlags() {
    return classAccessFlags;
  }

  public ProguardAccessFlags getNegatedClassAccessFlags() {
    return negatedClassAccessFlags;
  }

  public ProguardTypeMatcher getClassAnnotation() {
    return classAnnotation;
  }

  @Override
  public boolean equals(Object o) {
    if (!(o instanceof ProguardClassSpecification)) {
      return false;
    }
    ProguardClassSpecification that = (ProguardClassSpecification) o;

    if (classTypeNegated != that.classTypeNegated) {
      return false;
    }
    if (inheritanceIsExtends != that.inheritanceIsExtends) {
      return false;
    }
    if (!Objects.equals(classAnnotation, that.classAnnotation)) {
      return false;
    }
    if (!classAccessFlags.equals(that.classAccessFlags)) {
      return false;
    }
    if (!negatedClassAccessFlags.equals(that.negatedClassAccessFlags)) {
      return false;
    }
    if (classType != that.classType) {
      return false;
    }
    if (!classNames.equals(that.classNames)) {
      return false;
    }
    if (!Objects.equals(inheritanceAnnotation, that.inheritanceAnnotation)) {
      return false;
    }
    if (!Objects.equals(inheritanceClassName, that.inheritanceClassName)) {
      return false;
    }
    return memberRules.equals(that.memberRules);
  }

  @Override
  public int hashCode() {
    // Used multiplier 3 to avoid too much overflow when computing hashCode.
    int result = (classAnnotation != null ? classAnnotation.hashCode() : 0);
    result = 3 * result + classAccessFlags.hashCode();
    result = 3 * result + negatedClassAccessFlags.hashCode();
    result = 3 * result + (classTypeNegated ? 1 : 0);
    result = 3 * result + (classType != null ? classType.hashCode() : 0);
    result = 3 * result + classNames.hashCode();
    result = 3 * result + (inheritanceAnnotation != null ? inheritanceAnnotation.hashCode() : 0);
    result = 3 * result + (inheritanceClassName != null ? inheritanceClassName.hashCode() : 0);
    result = 3 * result + (inheritanceIsExtends ? 1 : 0);
    result = 3 * result + memberRules.hashCode();
    return result;
  }

  protected StringBuilder append(StringBuilder builder, boolean includeMemberRules) {
    StringUtils.appendNonEmpty(builder, "@", classAnnotation, null);
    StringUtils.appendNonEmpty(builder, "", classAccessFlags, null);
    StringUtils.appendNonEmpty(builder, "!", negatedClassAccessFlags.toString().replace(" ", " !"),
        null);
    if (builder.length() > 0) {
      builder.append(' ');
    }
    if (classTypeNegated) {
      builder.append('!');
    }
    builder.append(classType);
    builder.append(' ');
    classNames.writeTo(builder);
    if (hasInheritanceClassName()) {
      builder.append(inheritanceIsExtends ? "extends" : "implements");
      StringUtils.appendNonEmpty(builder, "@", inheritanceAnnotation, null);
      builder.append(' ');
      builder.append(inheritanceClassName);
    }
    if (includeMemberRules) {
      builder.append(" {\n");
      memberRules.forEach(memberRule -> {
        builder.append("  ");
        builder.append(memberRule);
        builder.append(";\n");
      });
      builder.append("}");
    }
    return builder;
  }

  /**
   * Short String representation without member rules.
   */
  public String toShortString() {
    return append(new StringBuilder(), false).toString();
  }

  @Override
  public String toString() {
    return append(new StringBuilder(), true).toString();
  }
}
