// Copyright (c) 2023, 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.

import DependenciesPlugin.Companion.computeRoot
import java.io.File
import java.nio.file.Paths
import java.security.MessageDigest
import java.util.UUID
import kotlin.reflect.full.declaredMemberProperties
import org.gradle.api.JavaVersion
import org.gradle.api.Plugin
import org.gradle.api.Project
import org.gradle.api.Task
import org.gradle.api.file.ConfigurableFileCollection
import org.gradle.api.file.DuplicatesStrategy
import org.gradle.api.plugins.JavaPluginExtension
import org.gradle.api.tasks.JavaExec
import org.gradle.api.tasks.SourceSet
import org.gradle.api.tasks.testing.Test
import org.gradle.jvm.tasks.Jar
import org.gradle.kotlin.dsl.register
import org.gradle.nativeplatform.platform.OperatingSystem
import org.gradle.nativeplatform.platform.internal.DefaultNativePlatform


class DependenciesPlugin: Plugin<Project> {

  override fun apply(target: Project) {
    // Setup all test tasks to listen after system properties passed in by test.py.
    val testTask = target.tasks.findByName("test") as Test?
    testTask?.configure(isR8Lib = false, r8Jar = null, r8LibMappingFile = null)
  }

  companion object {
    fun computeRoot(file: File) : File {
      var parent = file
      while (!parent.getName().equals("d8_r8")) {
        parent = parent.getParentFile()
      }
      return parent.getParentFile()
    }
  }
}

enum class Jdk(val folder : String) {
  JDK_8("jdk8"),
  JDK_9("openjdk-9.0.4"),
  JDK_11("jdk-11"),
  JDK_17("jdk-17"),
  JDK_21("jdk-21");

  fun isJdk8() : Boolean {
    return this == JDK_8
  }

  fun getThirdPartyDependency() : ThirdPartyDependency {
    val os: OperatingSystem = DefaultNativePlatform.getCurrentOperatingSystem()
    val subFolder : String
    if (os.isLinux) {
      subFolder = if(isJdk8()) "linux-x86" else "linux"
    } else if (os.isMacOsX) {
      subFolder = if(isJdk8()) "darwin-x86" else "osx"
    } else {
      assert(os.isWindows())
      if (isJdk8()) {
        throw RuntimeException("No Jdk8 on Windows")
      }
      subFolder = "windows"
    }
    return ThirdPartyDependency(
      name,
      Paths.get("third_party", "openjdk", folder, subFolder).toFile(),
      Paths.get("third_party", "openjdk", folder, "$subFolder.tar.gz.sha1").toFile())
  }
}

fun Test.configure(isR8Lib: Boolean, r8Jar: File?, r8LibMappingFile: File? = null) {
  TestConfigurationHelper.setupTestTask(this, isR8Lib, r8Jar, r8LibMappingFile)
}

fun Project.getRoot() : File {
  return computeRoot(this.projectDir)
}

// See https://datatracker.ietf.org/doc/html/rfc4122#section-4.3 for the algorithm.
fun uuid5(namespace: UUID, name: String): UUID? {
  val md = MessageDigest.getInstance("SHA-1")
  md.update(uuidToBytes(namespace))
  md.update(name.encodeToByteArray())
  val sha1Bytes = md.digest()
  // Set version 5 (upper 4 bits of octet 6).
  sha1Bytes[6] = (sha1Bytes[6].toInt() and 0x0f).toByte()
  sha1Bytes[6] = (sha1Bytes[6].toInt() or 0x50).toByte()
  // Set two upper bits of octet 8 to 10.
  sha1Bytes[8] = (sha1Bytes[8].toInt() and 0x3f).toByte()
  sha1Bytes[8] = (sha1Bytes[8].toInt() or 0x80).toByte()
  return uuidFromBytes(sha1Bytes)
}

private fun uuidFromBytes(data: ByteArray): UUID? {
  assert(data.size >= 16)
  return UUID(toNetworkOrder(data, 0), toNetworkOrder(data, 8))
}

private fun uuidToBytes(uuid: UUID): ByteArray? {
  val result = ByteArray(16)
  fromNetworkByteOrder(uuid.mostSignificantBits, result, 0)
  fromNetworkByteOrder(uuid.leastSignificantBits, result, 8)
  return result
}

private fun toNetworkOrder(data: ByteArray, dataIndex: Int): Long {
  var result: Long = 0
  for (i in 0..7) result = result shl 8 or (data[dataIndex + i].toInt() and 0xff).toLong()
  return result
}

private fun fromNetworkByteOrder(value: Long, dest: ByteArray, destIndex: Int) {
  for (i in 0..7) dest[i + destIndex] = (value shr (7 - i) * 8 and 0xffL).toByte()
}

fun Project.header(title : String) : String {
  return "****** ${title} ******"
}

/**
 * Builds a jar for each sub folder in a test source set.
 *
 * <p> As an example, src/test/examplesJava9 contains subfolders: backport, collectionof, ..., .
 * These are compiled to individual jars and placed in <repo-root>/build/test/examplesJava9/ as:
 * backport.jar, collectionof.jar, ..., .
 *
 * Calling this from a project will amend the task graph with the task named
 * getExamplesJarsTaskName(examplesName) such that it can be referenced from the test runners.
 */
fun Project.buildExampleJars(name : String) : Task {
  val jarTasks : MutableList<Task> = mutableListOf()
  val testSourceSet = extensions
    .getByType(JavaPluginExtension::class.java)
    .sourceSets
    // The TEST_SOURCE_SET_NAME is the source set defined by writing java { sourcesets.test { ... }}
    .getByName(SourceSet.TEST_SOURCE_SET_NAME)
  val destinationDir = getRoot().resolveAll("build", "test", name)
  val generateDir = getRoot().resolveAll("build", "generated", name)
  val classesOutput = destinationDir.resolve("classes")
  testSourceSet.java.destinationDirectory.set(classesOutput)
  testSourceSet.resources.destinationDirectory.set(destinationDir)
  testSourceSet
    .java
    .sourceDirectories
    .files
    .forEach { srcDir ->
      srcDir.listFiles(File::isDirectory)?.forEach { exampleDir ->
        arrayOf("compileTestJava", "debuginfo-all", "debuginfo-none").forEach { taskName ->
          if (!project.getTasksByName(taskName, false).isEmpty()) {
            var generationTask : Task? = null
            val compileOutput = getOutputName(classesOutput.toString(), taskName)
            if (exampleDir.resolve("TestGenerator.java").isFile) {
              val generatedOutput = Paths.get(
                getOutputName(generateDir.toString(), taskName), exampleDir.name).toString()
              generationTask = tasks.register<JavaExec>(
                "generate-$name-${exampleDir.name}-$taskName") {
                dependsOn(taskName)
                mainClass.set("${exampleDir.name}.TestGenerator")
                classpath = files(compileOutput, testSourceSet.compileClasspath)
                args(compileOutput, generatedOutput)
                outputs.dirs(generatedOutput)
              }.get()
            }
            jarTasks.add(tasks.register<Jar>("jar-$name-${exampleDir.name}-$taskName") {
              dependsOn(taskName)
              archiveFileName.set("${getOutputName(exampleDir.name, taskName)}.jar")
              destinationDirectory.set(destinationDir)
              duplicatesStrategy = DuplicatesStrategy.EXCLUDE
              if (generationTask != null) {
                // If a generation task exists, we first take the generated output and add to the
                // current jar. Running with DuplicatesStrategy.EXCLUDE ensure that we do not
                // overwrite with the non-generated file.
                dependsOn(generationTask)
                from(generationTask.outputs.files.singleFile.parentFile) {
                  include("${exampleDir.name}/**/*.class")
                  exclude("**/TestGenerator*")
                }
              }
              from(compileOutput) {
                include("${exampleDir.name}/**/*.class")
                exclude("**/TestGenerator*")
              }
              // Copy additional resources into the jar.
              from(exampleDir) {
                exclude("**/*.java")
                exclude("**/keep-rules*.txt")
                into(exampleDir.name)
              }
            }.get())
          }
        }
      }
    }
  return tasks.register(getExampleJarsTaskName(name)) {
    dependsOn(jarTasks.toTypedArray())
  }.get()
}

fun getOutputName(dest: String, taskName: String) : String {
  if (taskName.equals("compileTestJava")) {
    return dest
  }
  return "${dest}_${taskName.replace('-', '_')}"
}

fun Project.getExampleJarsTaskName(name: String) : String {
  return "build-example-jars-$name"
}

fun Project.resolve(
  thirdPartyDependency: ThirdPartyDependency, vararg paths: String,
) : ConfigurableFileCollection {
  return files(project.getRoot().resolve(thirdPartyDependency.path).resolveAll(*paths))
}

/**
 * When using composite builds, referecing tasks in other projects do not give a Task but a
 * TaskReference. To get outputs from other tasks we need to have a proper task and gradle do not
 * provide a way of getting a Task from a TaskReference. We use a trick where create a synthetic
 * task that depends on the task of interest, allowing us to look at the graph and obtain the
 * actual reference. Remove this code if gradle starts supporting this natively.
 */
fun Project.projectTask(project : String, taskName : String) : Task {
  val name = "$project-reference-$taskName";
  val task = tasks.register(name) {
    dependsOn(gradle.includedBuild(project).task(":$taskName"))
  }.get();
  return task.taskDependencies
    .getDependencies(tasks.getByName(name)).iterator().next();
}

fun File.resolveAll(vararg xs: String) : File {
  var that = this;
  for (x in xs) {
    that = that.resolve(x)
  }
  return that
}

fun Project.getJavaHome(jdk : Jdk) : File {
  val os: OperatingSystem = DefaultNativePlatform.getCurrentOperatingSystem()
  var osFolder = "linux"
  if (os.isWindows()) {
    osFolder = "windows"
  }
  if (os.isMacOsX) {
    osFolder = "osx/Contents/Home"
  }
  return getRoot().resolveAll("third_party", "openjdk", jdk.folder, osFolder)
}

fun Project.getCompilerPath(jdk : Jdk) : String {
  val os: OperatingSystem = DefaultNativePlatform.getCurrentOperatingSystem()
  val binary = if (os.isWindows()) "javac.exe" else "javac"
  return getJavaHome(jdk).resolveAll("bin", binary).toString()
}

fun Project.getJavaPath(jdk : Jdk) : String {
  val os: OperatingSystem = DefaultNativePlatform.getCurrentOperatingSystem()
  val binary = if (os.isWindows()) "java.exe" else "java"
  return getJavaHome(jdk).resolveAll("bin", binary).toString()
}

fun Project.getClasspath(vararg paths: File) : String {
  val os: OperatingSystem = DefaultNativePlatform.getCurrentOperatingSystem()
  assert (!paths.isEmpty())
  val separator = if (os.isWindows()) ";"  else ":"
  var classpath = paths.joinToString(separator = separator) { it -> it.toString() }
  return classpath
}

fun Project.baseCompilerCommandLine(
  jar: File, deps: File, compiler: String, args: List<String> = listOf(),
) : List<String> {
  // Execute r8 commands against a stable r8 with dependencies.
  // TODO(b/139725780): See if we can remove or lower the heap size (-Xmx8g).
  return listOf(
    getJavaPath(Jdk.JDK_17),
    "-Xmx8g",
    "-ea",
    "-cp",
    getClasspath(jar, deps),
    "com.android.tools.r8.SwissArmyKnife",
    compiler) + args
}

fun Project.baseCompilerCommandLine(
  jar: File, compiler: String, args: List<String> = listOf(),
) : List<String> {
  // Execute r8 commands against a stable r8 with dependencies.
  // TODO(b/139725780): See if we can remove or lower the heap size (-Xmx8g).
  return listOf(
    getJavaPath(Jdk.JDK_17),
    "-Xmx8g",
    "-ea",
    "-cp",
    "$jar",
    "com.android.tools.r8.SwissArmyKnife",
    compiler) + args
}

fun Project.createR8LibCommandLine(
  r8Compiler: File,
  input: File,
  output: File,
  pgConf: List<File>,
  excludingDepsVariant: Boolean,
  debugVariant: Boolean,
  lib: List<File> = listOf(),
  classpath: List<File> = listOf(),
  pgInputMap: File? = null,
) : List<String> {
  return buildList {
    add("python3")
    add("${getRoot().resolve("tools").resolve("create_r8lib.py")}")
    add("--r8compiler")
    add("${r8Compiler}")
    add("--r8jar")
    add("${input}")
    add("--output")
    add("${output}")
    pgConf.forEach { add("--pg-conf"); add("$it") }
    lib.forEach { add("--lib"); add("$it") }
    classpath.forEach { add("--classpath"); add("$it") }
    if (excludingDepsVariant) {
      add("--excldeps-variant")
    }
    if (debugVariant) {
      add("--debug-variant")
    }
    if (pgInputMap != null) {
      add("--pg-map")
      add("$pgInputMap")
    }
  }
}

object JvmCompatibility {
  val sourceCompatibility = JavaVersion.VERSION_11
  val targetCompatibility = JavaVersion.VERSION_11
}

object Versions {
  const val asmVersion = "9.6"
  const val errorproneVersion = "2.18.0"
  const val fastUtilVersion = "7.2.1"
  const val gsonVersion = "2.10.1"
  const val guavaVersion = "32.1.2-jre"
  const val javassist = "3.29.2-GA"
  const val junitVersion = "4.13-beta-2"
  const val kotlinVersion = "1.9.0"
  const val kotlinMetadataVersion = "0.9.0"
  const val mockito = "2.10.0"
  const val smaliVersion = "3.0.3"
}

object Deps {
  val asm by lazy { "org.ow2.asm:asm:${Versions.asmVersion}" }
  val asmUtil by lazy { "org.ow2.asm:asm-util:${Versions.asmVersion}" }
  val asmCommons by lazy { "org.ow2.asm:asm-commons:${Versions.asmVersion}" }
  val errorprone by lazy { "com.google.errorprone:error_prone_core:${Versions.errorproneVersion}" }
  val fastUtil by lazy { "it.unimi.dsi:fastutil:${Versions.fastUtilVersion}"}
  val gson by lazy { "com.google.code.gson:gson:${Versions.gsonVersion}"}
  val guava by lazy { "com.google.guava:guava:${Versions.guavaVersion}" }
  val javassist by lazy { "org.javassist:javassist:${Versions.javassist}"}
  val junit by lazy { "junit:junit:${Versions.junitVersion}"}
  val kotlinMetadata by lazy {
    "org.jetbrains.kotlinx:kotlinx-metadata-jvm:${Versions.kotlinMetadataVersion}" }
  val kotlinStdLib by lazy { "org.jetbrains.kotlin:kotlin-stdlib:${Versions.kotlinVersion}" }
  val kotlinReflect by lazy { "org.jetbrains.kotlin:kotlin-reflect:${Versions.kotlinVersion}" }
  val mockito by lazy { "org.mockito:mockito-core:${Versions.mockito}" }
  val smali by lazy { "com.android.tools.smali:smali:${Versions.smaliVersion}" }
  val smaliUtil by lazy { "com.android.tools.smali:smali-util:${Versions.smaliVersion}" }
}

object ThirdPartyDeps {
  val aapt2 = ThirdPartyDependency(
    "aapt2",
    Paths.get("third_party", "aapt2").toFile(),
    Paths.get("third_party", "aapt2.tar.gz.sha1").toFile())
  val androidJars = getThirdPartyAndroidJars()
  val androidVMs = getThirdPartyAndroidVms()
  val apiDatabase = ThirdPartyDependency(
    "apiDatabase",
    Paths.get("third_party", "api_database", "api_database").toFile(),
    Paths.get("third_party", "api_database", "api_database.tar.gz.sha1").toFile())
  val artTests = ThirdPartyDependency(
    "art-tests",
    Paths.get("tests", "2017-10-04", "art").toFile(),
    Paths.get("tests", "2017-10-04", "art.tar.gz.sha1").toFile())
  val artTestsLegacy = ThirdPartyDependency(
    "art-tests-legacy",
    Paths.get("tests", "2016-12-19", "art").toFile(),
    Paths.get("tests", "2016-12-19", "art.tar.gz.sha1").toFile())
  val clank = ThirdPartyDependency(
    "clank",
    Paths.get("third_party", "chrome", "clank_google3_prebuilt").toFile(),
    Paths.get("third_party", "chrome", "clank_google3_prebuilt.tar.gz.sha1").toFile(),
    DependencyType.X20)
  val chrome = ThirdPartyDependency(
    "chrome",
    Paths.get("third_party", "chrome", "chrome_200430").toFile(),
    Paths.get("third_party", "chrome", "chrome_200430.tar.gz.sha1").toFile(),
    DependencyType.X20)
  val compilerApi = ThirdPartyDependency(
    "compiler-api",
    Paths.get(
      "third_party", "binary_compatibility_tests", "compiler_api_tests").toFile(),
    Paths.get(
      "third_party",
      "binary_compatibility_tests",
      "compiler_api_tests.tar.gz.sha1").toFile())
  val composeExamplesChangedBitwiseValuePropagation = ThirdPartyDependency(
    "compose-examples-changed-bitwise-value-propagation",
    Paths.get(
      "third_party", "opensource-apps", "compose-examples",
      "changed-bitwise-value-propagation").toFile(),
    Paths.get(
      "third_party", "opensource-apps", "compose-examples",
      "changed-bitwise-value-propagation.tar.gz.sha1").toFile())
  val coreLambdaStubs = ThirdPartyDependency(
    "coreLambdaStubs",
    Paths.get("third_party", "core-lambda-stubs").toFile(),
    Paths.get("third_party", "core-lambda-stubs.tar.gz.sha1").toFile())
  val customConversion = ThirdPartyDependency(
    "customConversion",
    Paths.get("third_party", "openjdk", "custom_conversion").toFile(),
    Paths.get("third_party", "openjdk", "custom_conversion.tar.gz.sha1").toFile())
  val dagger = ThirdPartyDependency(
    "dagger",
    Paths.get("third_party", "dagger", "2.41").toFile(),
    Paths.get("third_party", "dagger", "2.41.tar.gz.sha1").toFile())
  val ddmLib = ThirdPartyDependency(
    "ddmlib",
    Paths.get("third_party", "ddmlib").toFile(),
    Paths.get("third_party", "ddmlib.tar.gz.sha1").toFile())
  val examples = ThirdPartyDependency(
    "examples",
    Paths.get("third_party", "examples").toFile(),
    Paths.get("third_party", "examples.tar.gz.sha1").toFile())
  val examplesAndroidN = ThirdPartyDependency(
    "examplesAndroidN",
    Paths.get("third_party", "examplesAndroidN").toFile(),
    Paths.get("third_party", "examplesAndroidN.tar.gz.sha1").toFile())
  val examplesAndroidO = ThirdPartyDependency(
    "examplesAndroidO",
    Paths.get("third_party", "examplesAndroidO").toFile(),
    Paths.get("third_party", "examplesAndroidO.tar.gz.sha1").toFile())
  val examplesAndroidOGenerated = ThirdPartyDependency(
    "examplesAndroidOGenerated",
    Paths.get("third_party", "examplesAndroidOGenerated").toFile(),
    Paths.get("third_party", "examplesAndroidOGenerated.tar.gz.sha1").toFile())
  val examplesAndroidOLegacy = ThirdPartyDependency(
    "examplesAndroidOLegacy",
    Paths.get("third_party", "examplesAndroidOLegacy").toFile(),
    Paths.get("third_party", "examplesAndroidOLegacy.tar.gz.sha1").toFile())
  val examplesAndroidP = ThirdPartyDependency(
    "examplesAndroidP",
    Paths.get("third_party", "examplesAndroidP").toFile(),
    Paths.get("third_party", "examplesAndroidP.tar.gz.sha1").toFile())
  val examplesAndroidPGenerated = ThirdPartyDependency(
    "examplesAndroidPGenerated",
    Paths.get("third_party", "examplesAndroidPGenerated").toFile(),
    Paths.get("third_party", "examplesAndroidPGenerated.tar.gz.sha1").toFile())
  val desugarJdkLibs = ThirdPartyDependency(
    "desugar-jdk-libs",
    Paths.get("third_party", "openjdk", "desugar_jdk_libs").toFile(),
    Paths.get("third_party", "openjdk", "desugar_jdk_libs.tar.gz.sha1").toFile())
  val desugarJdkLibsLegacy = ThirdPartyDependency(
    "desugar-jdk-libs-legacy",
    Paths.get("third_party", "openjdk", "desugar_jdk_libs_legacy").toFile(),
    Paths.get("third_party", "openjdk", "desugar_jdk_libs_legacy.tar.gz.sha1").toFile())
  val desugarLibraryReleases = getThirdPartyDesugarLibraryReleases()
  // TODO(b/289363570): This could probably be removed.
  val framework = ThirdPartyDependency(
    "framework",
    Paths.get("third_party", "framework").toFile(),
    Paths.get("third_party", "framework.tar.gz.sha1").toFile(),
    DependencyType.X20)
  val googleJavaFormat = ThirdPartyDependency(
    "google-java-format",
    Paths.get("third_party", "google-java-format").toFile(),
    Paths.get("third_party", "google-java-format.tar.gz.sha1").toFile())
  val googleJavaFormat_1_14 = ThirdPartyDependency(
    "google-java-format-1.14",
    Paths.get("third_party", "google", "google-java-format", "1.14.0").toFile(),
    Paths.get("third_party", "google", "google-java-format", "1.14.0.tar.gz.sha1").toFile())
  val googleYapf_20231013 = ThirdPartyDependency(
    "google-yapf-20231013",
    Paths.get("third_party", "google", "yapf", "20231013").toFile(),
    Paths.get("third_party", "google", "yapf", "20231013.tar.gz.sha1").toFile())
  val gson = ThirdPartyDependency(
    "gson",
    Paths.get("third_party", "gson", "gson-2.10.1").toFile(),
    Paths.get("third_party", "gson", "gson-2.10.1.tar.gz.sha1").toFile())
  val guavaJre = ThirdPartyDependency(
    "guava-jre",
    Paths.get("third_party", "guava", "guava-32.1.2-jre").toFile(),
    Paths.get("third_party", "guava", "guava-32.1.2-jre.tar.gz.sha1").toFile())
  val desugarJdkLibs11 = ThirdPartyDependency(
    "desugar-jdk-libs-11",
    Paths.get("third_party", "openjdk", "desugar_jdk_libs_11").toFile(),
    Paths.get("third_party", "openjdk", "desugar_jdk_libs_11.tar.gz.sha1").toFile())
  val gmscoreVersions = getGmsCoreVersions()
  val internalIssues = getInternalIssues()
  val jacoco = ThirdPartyDependency(
    "jacoco",
    Paths.get("third_party", "jacoco", "0.8.6").toFile(),
    Paths.get("third_party", "jacoco", "0.8.6.tar.gz.sha1").toFile())
  val jasmin = ThirdPartyDependency(
    "jasmin",
    Paths.get("third_party", "jasmin").toFile(),
    Paths.get("third_party", "jasmin.tar.gz.sha1").toFile())
  val jsr223 = ThirdPartyDependency(
    "jsr223",
    Paths.get("third_party", "jsr223-api-1.0").toFile(),
    Paths.get("third_party", "jsr223-api-1.0.tar.gz.sha1").toFile())
  val java8Runtime = ThirdPartyDependency(
    "openjdk-rt-1.8",
    Paths.get("third_party", "openjdk", "openjdk-rt-1.8").toFile(),
    Paths.get("third_party", "openjdk", "openjdk-rt-1.8.tar.gz.sha1").toFile())
  val jdks = getJdks()
  val jdk11Test = ThirdPartyDependency(
    "jdk-11-test",
    Paths.get("third_party", "openjdk", "jdk-11-test").toFile(),
    Paths.get("third_party", "openjdk", "jdk-11-test.tar.gz.sha1").toFile())
  val junit = ThirdPartyDependency(
    "junit",
    Paths.get("third_party", "junit").toFile(),
    Paths.get("third_party", "junit.tar.gz.sha1").toFile())
  val jdwpTests = ThirdPartyDependency(
    "jdwp-tests",
    Paths.get("third_party", "jdwp-tests").toFile(),
    Paths.get("third_party", "jdwp-tests.tar.gz.sha1").toFile())
  val kotlinCompilers = getThirdPartyKotlinCompilers()
  val kotlinR8TestResources = ThirdPartyDependency(
    "kotlinR8TestResources",
    Paths.get("third_party", "kotlinR8TestResources").toFile(),
    Paths.get("third_party", "kotlinR8TestResources.tar.gz.sha1").toFile())
  val kotlinxCoroutines = ThirdPartyDependency(
    "kotlinx-coroutines-1.3.6",
    Paths.get("third_party", "kotlinx-coroutines-1.3.6").toFile(),
    Paths.get("third_party", "kotlinx-coroutines-1.3.6.tar.gz.sha1").toFile())
  val multidex = ThirdPartyDependency(
    "multidex",
    Paths.get("third_party", "multidex").toFile(),
    Paths.get("third_party", "multidex.tar.gz.sha1").toFile())
  val nest = ThirdPartyDependency(
    "nest",
    Paths.get("third_party", "nest", "nest_20180926_7c6cfb").toFile(),
    Paths.get("third_party", "nest", "nest_20180926_7c6cfb.tar.gz.sha1").toFile(),
    DependencyType.X20)
  val proguards = getThirdPartyProguards()
  val proto = ThirdPartyDependency(
    "proto",
    Paths.get("third_party", "proto").toFile(),
    Paths.get("third_party", "proto.tar.gz.sha1").toFile(),
    DependencyType.X20)
  val protobufLite = ThirdPartyDependency(
    "protobuf-lite",
    Paths.get("third_party", "protobuf-lite").toFile(),
    Paths.get("third_party", "protobuf-lite.tar.gz.sha1").toFile(),
    DependencyType.X20)
  val r8 = ThirdPartyDependency(
    "r8",
    Paths.get("third_party", "r8").toFile(),
    Paths.get("third_party", "r8.tar.gz.sha1").toFile())
  val r8Mappings = ThirdPartyDependency(
    "r8-mappings",
    Paths.get("third_party", "r8mappings").toFile(),
    Paths.get("third_party", "r8mappings.tar.gz.sha1").toFile())
  val r8v2_0_74 = ThirdPartyDependency(
    "r8-v2-0-74",
    Paths.get("third_party", "r8-releases","2.0.74").toFile(),
    Paths.get("third_party", "r8-releases", "2.0.74.tar.gz.sha1").toFile())
  val r8v3_2_54 = ThirdPartyDependency(
    "r8-v3-2-54",
    Paths.get("third_party", "r8-releases","3.2.54").toFile(),
    Paths.get("third_party", "r8-releases", "3.2.54.tar.gz.sha1").toFile())
  val r8v8_0_46 = ThirdPartyDependency(
    "r8-v8-0-46",
    Paths.get("third_party", "r8-releases","8.0.46").toFile(),
    Paths.get("third_party", "r8-releases", "8.0.46.tar.gz.sha1").toFile())
  val retraceBenchmark = ThirdPartyDependency(
    "retrace-benchmark",
    Paths.get("third_party", "retrace_benchmark").toFile(),
    Paths.get("third_party", "retrace_benchmark.tar.gz.sha1").toFile())
  val retraceBinaryCompatibility = ThirdPartyDependency(
    "retrace-binary-compatibility",
    Paths.get("third_party", "retrace", "binary_compatibility").toFile(),
    Paths.get("third_party", "retrace", "binary_compatibility.tar.gz.sha1").toFile())
  val retracePartitionFormats = ThirdPartyDependency(
    "retrace-partition-formats",
    Paths.get("third_party", "retrace", "partition_formats").toFile(),
    Paths.get("third_party", "retrace", "partition_formats.tar.gz.sha1").toFile())
  val retraceInternal = ThirdPartyDependency(
    "retrace-internal",
    Paths.get("third_party", "retrace_internal").toFile(),
    Paths.get("third_party", "retrace_internal.tar.gz.sha1").toFile(),
    DependencyType.X20)
  val rhino = ThirdPartyDependency(
    "rhino",
    Paths.get("third_party", "rhino-1.7.10").toFile(),
    Paths.get("third_party", "rhino-1.7.10.tar.gz.sha1").toFile())
  val rhinoAndroid = ThirdPartyDependency(
    "rhino-android",
    Paths.get("third_party", "rhino-android-1.1.1").toFile(),
    Paths.get("third_party", "rhino-android-1.1.1.tar.gz.sha1").toFile())
  val smali = ThirdPartyDependency(
    "smali",
    Paths.get("third_party", "smali").toFile(),
    Paths.get("third_party", "smali.tar.gz.sha1").toFile())
  val tivi = ThirdPartyDependency(
    "tivi",
    Paths.get("third_party", "opensource-apps", "tivi").toFile(),
    Paths.get("third_party", "opensource-apps", "tivi.tar.gz.sha1").toFile())
}

fun getThirdPartyAndroidJars() : List<ThirdPartyDependency> {
  return listOf(
    "libcore_latest",
    "lib-master",
    "lib-v14",
    "lib-v15",
    "lib-v19",
    "lib-v21",
    "lib-v22",
    "lib-v23",
    "lib-v24",
    "lib-v25",
    "lib-v26",
    "lib-v27",
    "lib-v28",
    "lib-v29",
    "lib-v30",
    "lib-v31",
    "lib-v32",
    "lib-v33",
    "lib-v34"
  ).map(::getThirdPartyAndroidJar)
}

fun getThirdPartyAndroidJar(version : String) : ThirdPartyDependency {
  return ThirdPartyDependency(
    version,
    Paths.get("third_party", "android_jar", version).toFile(),
    Paths.get("third_party", "android_jar", "$version.tar.gz.sha1").toFile())
}

fun getThirdPartyAndroidVms() : List<ThirdPartyDependency> {
  return listOf(
    listOf("host", "art-master"),
    listOf("host", "art-14.0.0-beta3"),
    listOf("host", "art-13.0.0"),
    listOf("host", "art-12.0.0-beta4"),
    listOf("art-10.0.0"),
    listOf("art-5.1.1"),
    listOf("art-6.0.1"),
    listOf("art-7.0.0"),
    listOf("art-8.1.0"),
    listOf("art-9.0.0"),
    listOf("art"),
    listOf("dalvik-4.0.4"),
    listOf("dalvik")).map(::getThirdPartyAndroidVm)
}

fun getThirdPartyAndroidVm(version : List<String>) : ThirdPartyDependency {
  return ThirdPartyDependency(
    version.last(),
    Paths.get(
      "tools",
      "linux",
      *version.slice(0..version.size - 2).toTypedArray(),
      version.last()).toFile(),
    Paths.get(
      "tools",
      "linux",
      *version.slice(0..version.size - 2).toTypedArray(),
      "${version.last()}.tar.gz.sha1").toFile())
}

fun getJdks() : List<ThirdPartyDependency> {
  val os: OperatingSystem = DefaultNativePlatform.getCurrentOperatingSystem()
  if (os.isLinux || os.isMacOsX) {
    return Jdk.values().map{ it.getThirdPartyDependency()}
  } else {
    return Jdk.values().filter{ !it.isJdk8() }.map{ it.getThirdPartyDependency()}
  }
}

fun getThirdPartyProguards() : List<ThirdPartyDependency> {
  return listOf(
    "proguard5.2.1",
    "proguard6.0.1",
    "proguard-7.0.0",
    "proguard-7.3.2",
    "proguard-7.4.1")
    .map { ThirdPartyDependency(
      it,
      Paths.get("third_party", "proguard", it).toFile(),
      Paths.get("third_party", "proguard", "${it}.tar.gz.sha1").toFile())}
}

fun getThirdPartyKotlinCompilers() : List<ThirdPartyDependency> {
  return listOf(
    "kotlin-compiler-1.3.72",
    "kotlin-compiler-1.4.20",
    "kotlin-compiler-1.5.0",
    "kotlin-compiler-1.6.0",
    "kotlin-compiler-1.7.0",
    "kotlin-compiler-1.8.0",
    "kotlin-compiler-1.9.21",
    "kotlin-compiler-dev")
    .map { ThirdPartyDependency(
      it,
      Paths.get("third_party", "kotlin", it).toFile(),
      Paths.get("third_party", "kotlin", "${it}.tar.gz.sha1").toFile())}
}

fun getThirdPartyDesugarLibraryReleases() : List<ThirdPartyDependency> {
  return listOf(
    "1.0.9",
    "1.0.10",
    "1.1.0",
    "1.1.1",
    "1.1.5",
    "2.0.3")
    .map { ThirdPartyDependency(
      "desugar-library-release-$it",
      Paths.get("third_party", "openjdk", "desugar_jdk_libs_releases", it).toFile(),
      Paths.get("third_party", "openjdk", "desugar_jdk_libs_releases", "${it}.tar.gz.sha1").toFile())}
}

fun getInternalIssues() : List<ThirdPartyDependency> {
  return listOf("issue-127524985")
    .map { ThirdPartyDependency(
      "internal-$it",
      Paths.get("third_party", "internal", it).toFile(),
      Paths.get("third_party", "internal", "${it}.tar.gz.sha1").toFile(),
      DependencyType.X20)}
}

fun getGmsCoreVersions() : List<ThirdPartyDependency> {
  return listOf(
    "gmscore_v10",
    "latest")
    .map { ThirdPartyDependency(
      "gmscore-version-$it",
      Paths.get("third_party", "gmscore", it).toFile(),
      Paths.get("third_party", "gmscore", "${it}.tar.gz.sha1").toFile(),
      DependencyType.X20)}
}

private fun Project.allDependencies() : List<ThirdPartyDependency> {
  val allDeps = mutableListOf<ThirdPartyDependency>()
  ThirdPartyDeps::class.declaredMemberProperties.forEach {
    val value = it.get(ThirdPartyDeps)
    if (value is List<*>) {
      allDeps.addAll(value as List<ThirdPartyDependency>)
    } else {
      allDeps.add(value as ThirdPartyDependency)
    }
  }
  return allDeps
}

fun Project.allPublicDependencies() : List<ThirdPartyDependency> {
  return allDependencies().filter { x -> x.type == DependencyType.GOOGLE_STORAGE }
}

fun Project.allInternalDependencies() : List<ThirdPartyDependency> {
  return allDependencies().filter { x -> x.type == DependencyType.X20 }
}
