// Copyright (c) 2018, 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.kotlin;

import static junit.framework.TestCase.assertEquals;
import static junit.framework.TestCase.assertTrue;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.fail;

import com.android.tools.r8.graph.DexClass;
import com.android.tools.r8.graph.DexType;
import com.android.tools.r8.ir.optimize.lambda.CaptureSignature;
import com.android.tools.r8.utils.AndroidApp;
import com.android.tools.r8.utils.DexInspector;
import com.android.tools.r8.utils.InternalOptions;
import com.google.common.collect.Lists;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.concurrent.ExecutionException;
import java.util.function.Consumer;
import org.junit.Test;

public class KotlinLambdaMergingTest extends AbstractR8KotlinTestBase {
  private static final String KOTLIN_FUNCTION_IFACE = "Lkotlin/jvm/functions/Function";
  private static final String KOTLIN_FUNCTION_IFACE_STR = "kotlin.jvm.functions.Function";
  private static final String KEEP_INNER_AND_ENCLOSING =
      "-keepattributes InnerClasses,EnclosingMethod\n";
  private static final String KEEP_SIGNATURE_INNER_ENCLOSING =
      "-keepattributes Signature,InnerClasses,EnclosingMethod\n";
  private Consumer<InternalOptions> optionsModifier =
      opts -> {
        opts.enableClassInlining = false;
        // Ensure that enclosing method and inner class attributes are kept even on classes that are
        // not explicitly mentioned by a keep rule.
        opts.forceProguardCompatibility = true;
      };

  abstract static class LambdaOrGroup {
    abstract boolean match(DexClass clazz);
  }

  static class Group extends LambdaOrGroup {
    final String pkg;
    final String capture;
    final int arity;
    final String sam;
    final int singletons;

    private Group(String pkg, String capture, int arity, String sam, int singletons) {
      this.pkg = pkg;
      this.capture = fixCapture(capture);
      this.arity = arity;
      this.sam = sam;
      this.singletons = singletons;
    }

    private String fixCapture(String capture) {
      capture += "I";
      char[] chars = capture.toCharArray();
      Arrays.sort(chars);
      return new String(chars);
    }

    @Override
    public String toString() {
      return "group class " +
          (pkg.length() == 0 ? "" : pkg + "/") +
          "-$$LambdaGroup$XXXX (arity: " + arity +
          ", capture: " + capture + ", iface: " + sam + ", sing: " + singletons + ")";
    }

    @Override
    boolean match(DexClass clazz) {
      return clazz.type.getPackageDescriptor().equals(pkg) &&
          getLambdaOrGroupCapture(clazz).equals(capture) &&
          getLambdaSam(clazz).equals(sam) &&
          getLambdaSingletons(clazz) == singletons &&
          getLambdaOrGroupArity(clazz) == arity;
    }
  }

  private static Group kstyleImpl(String pkg, String capture, int arity, int singletons) {
    assertEquals(capture.isEmpty(), singletons != 0);
    return new Group(pkg, capture, arity, KOTLIN_FUNCTION_IFACE_STR + arity, singletons);
  }

  static Group kstyle(String pkg, int arity, int singletons) {
    assertTrue(singletons != 0);
    return kstyleImpl(pkg, "", arity, singletons);
  }

  private static Group kstyle(String pkg, String capture, int arity) {
    assertFalse(capture.isEmpty());
    return kstyleImpl(pkg, capture, arity, 0);
  }

  private static Group jstyleImpl(
      String pkg, String capture, int arity, String sam, int singletons) {
    assertTrue(capture.isEmpty() || singletons == 0);
    return new Group(pkg, capture, arity, sam, singletons);
  }

  private static Group jstyle(String pkg, String capture, int arity, String sam) {
    return jstyleImpl(pkg, capture, arity, sam, 0);
  }

  private static Group jstyle(String pkg, int arity, String sam, int singletons) {
    return jstyleImpl(pkg, "", arity, sam, singletons);
  }

  static class Lambda extends LambdaOrGroup {
    final String pkg;
    final String name;
    final int arity;

    Lambda(String pkg, String name, int arity) {
      this.pkg = pkg;
      this.name = name;
      this.arity = arity;
    }

    @Override
    public String toString() {
      return "lambda class " +
          (pkg.length() == 0 ? "" : pkg + "/") +
          name + " (arity: " + arity + ")";
    }

    @Override
    boolean match(DexClass clazz) {
      return clazz.type.getPackageDescriptor().equals(pkg) &&
          clazz.type.getName().equals(name) &&
          getLambdaOrGroupArity(clazz) == arity;
    }
  }

  static class Verifier {
    final DexInspector dexInspector;
    final List<DexClass> lambdas = new ArrayList<>();
    final List<DexClass> groups = new ArrayList<>();

    Verifier(AndroidApp app) throws IOException, ExecutionException {
      this(new DexInspector(app));
    }

    Verifier(DexInspector dexInspector) {
      this.dexInspector = dexInspector;
      initGroupsAndLambdas();
    }

    private void initGroupsAndLambdas() {
      dexInspector.forAllClasses(clazz -> {
        DexClass dexClass = clazz.getDexClass();
        if (isLambdaOrGroup(dexClass)) {
          if (isLambdaGroupClass(dexClass)) {
            groups.add(dexClass);
          } else {
            lambdas.add(dexClass);
          }
        }
      });
    }

    void assertLambdaGroups(Group... groups) {
      assertLambdasOrGroups("Lambda group", this.groups, groups);
    }

    void assertLambdas(Lambda... lambdas) {
      assertLambdasOrGroups("Lambda", this.lambdas, lambdas);
    }

    @SafeVarargs
    private static <T extends LambdaOrGroup>
    void assertLambdasOrGroups(String what, List<DexClass> objects, T... checks) {
      ArrayList<DexClass> list = Lists.newArrayList(objects);
      for (int i = 0; i < checks.length; i++) {
        T check = checks[i];
        for (DexClass clazz : list) {
          if (check.match(clazz)) {
            // Validate static initializer.
            if (check instanceof Group) {
              assertEquals(clazz.directMethods().length, ((Group) check).singletons == 0 ? 1 : 2);
            }

            list.remove(clazz);
            checks[i] = null;
            break;
          }
        }
      }

      int notFound = 0;
      for (T check : checks) {
        if (check != null) {
          System.err.println(what + " not found: " + check);
          notFound++;
        }
      }

      for (DexClass dexClass : list) {
        System.err.println(what + " unexpected: " +
            dexClass.type.descriptor.toString() +
            ", arity: " + getLambdaOrGroupArity(dexClass) +
            ", capture: " + getLambdaOrGroupCapture(dexClass) +
            ", sam: " + getLambdaSam(dexClass) +
            ", sing: " + getLambdaSingletons(dexClass));
        notFound++;
      }

      assertTrue(what + "s match failed", 0 == notFound && 0 == list.size());
    }
  }

  private static int getLambdaOrGroupArity(DexClass clazz) {
    if (isKStyleLambdaOrGroup(clazz)) {
      for (DexType iface : clazz.interfaces.values) {
        String descr = iface.descriptor.toString();
        if (descr.startsWith(KOTLIN_FUNCTION_IFACE)) {
          return Integer.parseInt(
              descr.substring(KOTLIN_FUNCTION_IFACE.length(), descr.length() - 1));
        }
      }

    } else {
      assertTrue(isJStyleLambdaOrGroup(clazz));
      // Taking the number of any virtual method parameters seems to be good enough.
      assertTrue(clazz.virtualMethods().length > 0);
      return clazz.virtualMethods()[0].method.proto.parameters.size();
    }
    fail("Failed to get arity for " + clazz.type.descriptor.toString());
    throw new AssertionError();
  }

  private static String getLambdaSam(DexClass clazz) {
    assertEquals(1, clazz.interfaces.size());
    return clazz.interfaces.values[0].toSourceString();
  }

  private static int getLambdaSingletons(DexClass clazz) {
    assertEquals(1, clazz.interfaces.size());
    return clazz.staticFields().length;
  }

  private static boolean isLambdaOrGroup(DexClass clazz) {
    return !clazz.type.getPackageDescriptor().startsWith("kotlin") &&
        (isKStyleLambdaOrGroup(clazz) || isJStyleLambdaOrGroup(clazz));
  }

  private static boolean isKStyleLambdaOrGroup(DexClass clazz) {
    return clazz.superType.descriptor.toString().equals("Lkotlin/jvm/internal/Lambda;");
  }

  private static boolean isJStyleLambdaOrGroup(DexClass clazz) {
    return clazz.superType.descriptor.toString().equals("Ljava/lang/Object;") &&
        clazz.interfaces.size() == 1;
  }

  private static boolean isLambdaGroupClass(DexClass clazz) {
    return clazz.type.getName().startsWith("-$$LambdaGroup$");
  }

  private static String getLambdaOrGroupCapture(DexClass clazz) {
    return CaptureSignature.getCaptureSignature(clazz.instanceFields());
  }

  @Test
  public void testTrivialKs() throws Exception {
    final String mainClassName = "lambdas_kstyle_trivial.MainKt";
    runTest("lambdas_kstyle_trivial", mainClassName, optionsModifier, (app) -> {
      Verifier verifier = new Verifier(app);
      String pkg = "lambdas_kstyle_trivial";

      verifier.assertLambdaGroups(
          allowAccessModification ?
              new Group[]{
                  kstyle("", 0, 4),
                  kstyle("", 1, 8),
                  kstyle("", 2, 2), // -\
                  kstyle("", 2, 5), // - 3 groups different by main method
                  kstyle("", 2, 4), // -/
                  kstyle("", 3, 2),
                  kstyle("", 22, 2)} :
              new Group[]{
                  kstyle(pkg, 0, 2),
                  kstyle(pkg, 1, 4),
                  kstyle(pkg, 2, 5), // - 2 groups different by main method
                  kstyle(pkg, 2, 4), // -/
                  kstyle(pkg, 3, 2),
                  kstyle(pkg, 22, 2),
                  kstyle(pkg + "/inner", 0, 2),
                  kstyle(pkg + "/inner", 1, 4)}
      );

      verifier.assertLambdas(
          allowAccessModification ?
              new Lambda[]{
                  new Lambda(pkg, "MainKt$testStateless$6", 1) /* Banned for limited inlining */} :
              new Lambda[]{
                  new Lambda(pkg, "MainKt$testStateless$6", 1), /* Banned for limited inlining */
                  new Lambda(pkg, "MainKt$testStateless$8", 2),
                  new Lambda(pkg + "/inner", "InnerKt$testInnerStateless$7", 2)}

      );
    });
  }

  @Test
  public void testCapturesKs() throws Exception {
    final String mainClassName = "lambdas_kstyle_captures.MainKt";
    runTest("lambdas_kstyle_captures", mainClassName, optionsModifier, (app) -> {
      Verifier verifier = new Verifier(app);
      String pkg = "lambdas_kstyle_captures";
      String grpPkg = allowAccessModification ? "" : pkg;

      verifier.assertLambdaGroups(
          kstyle(grpPkg, "LLL", 0),
          kstyle(grpPkg, "ILL", 0),
          kstyle(grpPkg, "III", 0),
          kstyle(grpPkg, "BCDFIJLLLLSZ", 0),
          kstyle(grpPkg, "BCDFIJLLSZ", 0)
      );

      verifier.assertLambdas(
          new Lambda(pkg, "MainKt$test1$15", 0),
          new Lambda(pkg, "MainKt$test2$10", 0),
          new Lambda(pkg, "MainKt$test2$11", 0),
          new Lambda(pkg, "MainKt$test2$9", 0)
      );
    });
  }

  @Test
  public void testGenericsNoSignatureKs() throws Exception {
    final String mainClassName = "lambdas_kstyle_generics.MainKt";
    runTest("lambdas_kstyle_generics", mainClassName, optionsModifier, (app) -> {
      Verifier verifier = new Verifier(app);
      String pkg = "lambdas_kstyle_generics";
      String grpPkg = allowAccessModification ? "" : pkg;

      verifier.assertLambdaGroups(
          kstyle(grpPkg, 1, 3), // Group for Any
          kstyle(grpPkg, "L", 1), // Group for Beta
          kstyle(grpPkg, "LS", 1), // Group for Gamma
          kstyle(grpPkg, 1, 2)  // Group for int
      );

      verifier.assertLambdas(
          new Lambda(pkg, "MainKt$main$4", 1)
      );
    });
  }

  @Test
  public void testInnerClassesAndEnclosingMethodsKs() throws Exception {
    final String mainClassName = "lambdas_kstyle_generics.MainKt";
    runTest("lambdas_kstyle_generics", mainClassName,
        KEEP_INNER_AND_ENCLOSING, optionsModifier, (app) -> {
          Verifier verifier = new Verifier(app);
          String pkg = "lambdas_kstyle_generics";
          String grpPkg = allowAccessModification ? "" : pkg;

          verifier.assertLambdaGroups(
              kstyle(grpPkg, 1, 3), // Group for Any
              kstyle(grpPkg, "L", 1), // Group for Beta   // First
              kstyle(grpPkg, "L", 1), // Group for Beta   // Second
              kstyle(grpPkg, "LS", 1), // Group for Gamma // First
              kstyle(grpPkg, "LS", 1), // Group for Gamma // Second
              kstyle(grpPkg, 1, 2)  // Group for int
          );

          verifier.assertLambdas(
              new Lambda(pkg, "MainKt$main$4", 1)
          );
        });
  }

  @Test
  public void testGenericsSignatureInnerEnclosingKs() throws Exception {
    final String mainClassName = "lambdas_kstyle_generics.MainKt";
    runTest("lambdas_kstyle_generics", mainClassName,
        KEEP_SIGNATURE_INNER_ENCLOSING, optionsModifier, (app) -> {
          Verifier verifier = new Verifier(app);
          String pkg = "lambdas_kstyle_generics";
          String grpPkg = allowAccessModification ? "" : pkg;

          verifier.assertLambdaGroups(
              kstyle(grpPkg, 1, 3), // Group for Any
              kstyle(grpPkg, "L", 1), // Group for Beta in First
              kstyle(grpPkg, "L", 1), // Group for Beta in Second
              kstyle(grpPkg, "LS", 1), // Group for Gamma<String> in First
              kstyle(grpPkg, "LS", 1), // Group for Gamma<Integer> in First
              kstyle(grpPkg, "LS", 1), // Group for Gamma<String> in Second
              kstyle(grpPkg, "LS", 1), // Group for Gamma<Integer> in Second
              kstyle(grpPkg, 1, 2)  // Group for int
          );

          verifier.assertLambdas(
              new Lambda(pkg, "MainKt$main$4", 1)
          );
        });
  }

  @Test
  public void testTrivialJs() throws Exception {
    final String mainClassName = "lambdas_jstyle_trivial.MainKt";
    runTest("lambdas_jstyle_trivial", mainClassName, optionsModifier, (app) -> {
      Verifier verifier = new Verifier(app);
      String pkg = "lambdas_jstyle_trivial";
      String grp = allowAccessModification ? "" : pkg;

      String supplier = "lambdas_jstyle_trivial.Lambdas$Supplier";
      String intSupplier = "lambdas_jstyle_trivial.Lambdas$IntSupplier";
      String consumer = "lambdas_jstyle_trivial.Lambdas$Consumer";
      String intConsumer = "lambdas_jstyle_trivial.Lambdas$IntConsumer";
      String multiFunction = "lambdas_jstyle_trivial.Lambdas$MultiFunction";

      verifier.assertLambdaGroups(
          jstyle(grp, 0, intSupplier, 2),
          jstyle(grp, "L", 0, supplier),
          jstyle(grp, "LL", 0, supplier),
          jstyle(grp, "LLL", 0, supplier),
          jstyle(grp, 1, intConsumer, allowAccessModification ? 3 : 2),
          jstyle(grp, "I", 1, consumer),
          jstyle(grp, "II", 1, consumer),
          jstyle(grp, "III", 1, consumer),
          jstyle(grp, "IIII", 1, consumer),
          jstyle(grp, 3, multiFunction, 2),
          jstyle(grp, 3, multiFunction, 2),
          jstyle(grp, 3, multiFunction, 4),
          jstyle(grp, 3, multiFunction, 6)
      );

      verifier.assertLambdas(
          allowAccessModification ?
              new Lambda[]{
                  new Lambda(pkg + "/inner", "InnerKt$testInner1$4", 1),
                  new Lambda(pkg + "/inner", "InnerKt$testInner1$5", 1)
              } :
              new Lambda[]{
                  new Lambda(pkg + "/inner", "InnerKt$testInner1$1", 1),
                  new Lambda(pkg + "/inner", "InnerKt$testInner1$2", 1),
                  new Lambda(pkg + "/inner", "InnerKt$testInner1$3", 1),
                  new Lambda(pkg + "/inner", "InnerKt$testInner1$4", 1),
                  new Lambda(pkg + "/inner", "InnerKt$testInner1$5", 1)
              }

      );
    });
  }

  @Test
  public void testSingleton() throws Exception {
    final String mainClassName = "lambdas_singleton.MainKt";
    runTest("lambdas_singleton", mainClassName, optionsModifier, (app) -> {
      Verifier verifier = new Verifier(app);
      String pkg = "lambdas_singleton";
      String grp = allowAccessModification ? "" : pkg;

      verifier.assertLambdaGroups(
          kstyle(grp, 1, 1 /* 1 out of 5 lambdas in the group */),
          jstyle(grp, 2, "java.util.Comparator", 0 /* 0 out of 2 lambdas in the group */)
      );

      verifier.assertLambdas(/* None */);
    });
  }
}
