package org.checkerframework.checker.nullness;

import com.sun.source.tree.ExpressionTree;
import java.util.LinkedHashSet;
import java.util.List;
import java.util.Set;
import javax.lang.model.element.AnnotationMirror;
import javax.lang.model.type.TypeKind;
import javax.lang.model.type.TypeMirror;
import org.checkerframework.checker.nullness.qual.KeyFor;
import org.checkerframework.checker.nullness.qual.Nullable;
import org.checkerframework.framework.flow.CFAbstractAnalysis;
import org.checkerframework.framework.flow.CFAbstractValue;
import org.checkerframework.javacutil.AnnotationUtils;

/**
 * KeyForValue holds additional information about which maps this value is a key for. This extra
 * information is required when adding the @KeyFor qualifier to the type is not a refinement of the
 * type. For example,
 *
 * <pre>
 * {@code Map<T, Object> map = ...;}
 * {@code <T> T method(T param) { }
 *   if (map.contains(param) {
 *     {@code @NonNull Object o = map.get(param);}
 *     return param;
 *   }
 * }
 * }</pre>
 *
 * Inside the if statement, {@code param} is a key for "map". This would normally be represented as
 * {@code @KeyFor("map") T}, but this is not a subtype of {@code T}, so the type cannot be refined.
 * Instead, the value for {@code param} includes "map" in the list of keyForMaps. This information
 * is used in {@link KeyForAnnotatedTypeFactory#isKeyForMap(String, ExpressionTree)}.
 */
public class KeyForValue extends CFAbstractValue<KeyForValue> {
  /**
   * If the underlying type is a type variable or a wildcard, then this is a set of maps for which
   * this value is a key. Otherwise, it's null.
   */
  // Cannot be final because lub re-assigns; add a new constructor to do this cleanly?
  private @Nullable Set<String> keyForMaps;

  /** Create an instance. */
  public KeyForValue(
      CFAbstractAnalysis<KeyForValue, ?, ?> analysis,
      Set<AnnotationMirror> annotations,
      TypeMirror underlyingType) {
    super(analysis, annotations, underlyingType);
    KeyForAnnotatedTypeFactory atypeFactory =
        (KeyForAnnotatedTypeFactory) analysis.getTypeFactory();
    AnnotationMirror keyfor = atypeFactory.getAnnotationByClass(annotations, KeyFor.class);
    if (keyfor != null
        && (underlyingType.getKind() == TypeKind.TYPEVAR
            || underlyingType.getKind() == TypeKind.WILDCARD)) {
      List<String> list =
          AnnotationUtils.getElementValueArray(
              keyfor, atypeFactory.keyForValueElement, String.class);
      keyForMaps = new LinkedHashSet<>(list.size());
      keyForMaps.addAll(list);
    } else {
      keyForMaps = null;
    }
  }

  /**
   * If the underlying type is a type variable or a wildcard, then this is a set of maps for which
   * this value is a key. Otherwise, it's null.
   */
  public Set<String> getKeyForMaps() {
    return keyForMaps;
  }

  @Override
  public KeyForValue leastUpperBound(KeyForValue other) {
    KeyForValue lub = super.leastUpperBound(other);
    if (other == null || other.keyForMaps == null || this.keyForMaps == null) {
      return lub;
    }
    // Lub the keyForMaps by intersecting the sets.
    lub.keyForMaps = new LinkedHashSet<>(this.keyForMaps.size());
    lub.keyForMaps.addAll(this.keyForMaps);
    lub.keyForMaps.retainAll(other.keyForMaps);
    if (lub.keyForMaps.isEmpty()) {
      lub.keyForMaps = null;
    }
    return lub;
  }

  @Override
  public KeyForValue mostSpecific(KeyForValue other, KeyForValue backup) {
    KeyForValue mostSpecific = super.mostSpecific(other, backup);
    if (mostSpecific == null) {
      if (other == null) {
        return this;
      }
      // mostSpecific is null if the two types are not comparable.  This is normally
      // because one of this or other is a type variable and annotations is empty, but the
      // other annotations are not empty.  In this case, copy the keyForMaps and to the
      // value with the no annotations and return it as most specific.
      if (other.getAnnotations().isEmpty()) {
        other.addKeyFor(this.keyForMaps);
        return other;
      } else if (this.getAnnotations().isEmpty()) {
        this.addKeyFor(other.keyForMaps);
        return this;
      }
      return null;
    }

    mostSpecific.addKeyFor(this.keyForMaps);
    if (other != null) {
      mostSpecific.addKeyFor(other.keyForMaps);
    }
    return mostSpecific;
  }

  private void addKeyFor(Set<String> newKeyForMaps) {
    if (newKeyForMaps == null || newKeyForMaps.isEmpty()) {
      return;
    }
    if (keyForMaps == null) {
      keyForMaps = new LinkedHashSet<>();
    }
    keyForMaps.addAll(newKeyForMaps);
  }
}
