diff --git a/gradle.properties b/gradle.properties
deleted file mode 100644
index 4bd94ac..0000000
--- a/gradle.properties
+++ /dev/null
@@ -1,17 +0,0 @@
-# Copyright (c) 2020, 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.
-
-org.gradle.jvmargs=-Xmx2048M -Dfile.encoding=UTF-8
-kotlin.daemon.jvmargs=-Xmx3g -Dkotlin.js.compiler.legacy.force_enabled=true
-systemProp.file.encoding=UTF-8
-
-# Enable new incremental compilation
-kotlin.incremental.useClasspathSnapshot=true
-
-org.gradle.parallel=true
-org.gradle.caching=false
-
-# Do not download any jdks or detect them. We provide them
-org.gradle.java.installations.auto-detect=false
-org.gradle.java.installations.auto-download=false
diff --git a/old.gradle.deprecated b/old.gradle.deprecated
deleted file mode 100644
index f7b3a44..0000000
--- a/old.gradle.deprecated
+++ /dev/null
@@ -1,1844 +0,0 @@
-// Copyright (c) 2016, 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 net.ltgt.gradle.errorprone.CheckSeverity
-import org.gradle.internal.os.OperatingSystem
-import tasks.DownloadDependency
-
-plugins {
-  id "net.ltgt.errorprone" version "2.0.2"
-}
-
-apply plugin: 'java'
-apply plugin: 'idea'
-
-ext {
-    // When updating dependencies also update and run
-    // tools/create_local_maven_with_dependencies.py
-    androidSupportVersion = '25.4.0'
-    asmVersion = '9.5'  // When updating update tools/asmifier.py, build.src and Toolhelper as well.
-    javassistVersion = '3.29.2-GA'
-    espressoVersion = '3.0.0'
-    fastutilVersion = '7.2.1'
-    guavaVersion = '31.1-jre'
-    gsonVersion = '2.10.1'
-    junitVersion = '4.13-beta-2'
-    mockitoVersion = '2.10.0'
-    // The kotlin version is only here to specify the kotlin language level,
-    // all kotlin compilations are done in tests.
-    kotlinVersion = '1.8.0'
-    kotlinExtMetadataJVMVersion = '0.7.0'
-    smaliVersion = '3.0.3'
-    errorproneVersion = '2.18.0'
-    testngVersion = '6.10'
-}
-
-repositories {
-    maven {
-        url uri('file:third_party/dependencies')
-    }
-}
-
-if (project.hasProperty('with_code_coverage')) {
-    apply plugin: 'jacoco'
-}
-
-// Custom source set for example tests and generated tests.
-sourceSets {
-    main {
-        java {
-            srcDirs = ['src/main/java', 'src/keepanno/java']
-            // Exclude in old setup, resource shrinker is only compiled into R8 with 8.0
-            exclude 'com/android/tools/r8/utils/resourceshrinker/*.java'
-        }
-        resources {
-            srcDirs "third_party/api_database/api_database"
-        }
-    }
-    main17 {
-        java {
-            srcDirs = ['src/main/java', 'src/keepanno/java']
-            // Exclude in old setup, resource shrinker is only compiled into R8 with 8.0
-            exclude 'com/android/tools/r8/utils/resourceshrinker/*.java'
-        }
-        resources {
-            srcDirs "third_party/api_database/api_database"
-        }
-    }
-    test {
-        java {
-            srcDirs = [
-                    'src/test/java',
-                    'src/test/bootstrap',
-                    'build/generated/test/java',
-            ]
-        }
-    }
-    apiUsageSample {
-        java {
-            srcDirs = ['src/test/apiUsageSample', 'src/main/java']
-            include 'com/android/tools/apiusagesample/*.java'
-            include 'com/android/tools/r8/BaseCompilerCommandParser.java'
-            include 'com/android/tools/r8/D8CommandParser.java'
-            include 'com/android/tools/r8/R8CommandParser.java'
-            include 'com/android/tools/r8/utils/FlagFile.java'
-        }
-    }
-    cfSegments {
-        java {
-            srcDirs = ['third_party/classlib/java', 'src/cf_segments/java']
-        }
-        output.resourcesDir = 'build/classes/cfSegments'
-    }
-    debugTestResources {
-        java {
-            srcDirs = ['src/test/debugTestResources']
-        }
-        output.resourcesDir = 'build/classes/debugTestResources'
-    }
-    debugTestResourcesJava8 {
-        java {
-            srcDirs = ['src/test/debugTestResourcesJava8']
-        }
-        output.resourcesDir = 'build/classes/debugTestResourcesJava8'
-    }
-    examplesJava9 {
-        java {
-            srcDirs = ['src/test/examplesJava9']
-        }
-    }
-    examplesJava10 {
-        java {
-            srcDirs = ['src/test/examplesJava10']
-        }
-    }
-    examplesJava11 {
-        java {
-            srcDirs = ['src/test/examplesJava11']
-        }
-    }
-    examplesJava17 {
-        java {
-            srcDirs = ['src/test/examplesJava17']
-        }
-    }
-    examplesJava20 {
-        java {
-            srcDirs = ['src/test/examplesJava20']
-        }
-    }
-    keepanno {
-        java {
-            srcDirs = ['src/keepanno/java']
-            include 'com/android/tools/r8/keepanno/annotations/*.java'
-        }
-    }
-}
-
-// Ensure importing into IntelliJ IDEA use the same output directories as Gradle. In tests we
-// use the output path for tests (ultimately through ToolHelper.getClassPathForTests()) and
-// therefore these paths need to be the same. See https://youtrack.jetbrains.com/issue/IDEA-175172
-// for context.
-idea {
-    sourceSets.all { SourceSet sources ->
-        module {
-            if (sources.name == "main") {
-                sourceDirs += sources.java.srcDirs
-                outputDir sources.output.classesDirs[0]
-            } else {
-                testSourceDirs += sources.java.srcDirs
-                testOutputDir sources.output.classesDirs[0]
-            }
-        }
-    }
-}
-
-dependencies {
-    implementation "com.google.code.gson:gson:$gsonVersion"
-    // Include all of guava when compiling the code, but exclude annotations that we don't
-    // need from the packaging.
-    compileOnly("com.google.guava:guava:$guavaVersion")
-    implementation("com.google.guava:guava:$guavaVersion", {
-        exclude group: 'com.google.errorprone'
-        exclude group: 'com.google.code.findbugs'
-        exclude group: 'com.google.j2objc'
-        exclude group: 'org.codehaus.mojo'
-        exclude group: 'com.google.guava', module: 'listenablefuture'
-        exclude group: 'com.google.guava', module: 'failureaccess'
-    })
-    implementation group: 'it.unimi.dsi', name: 'fastutil', version: fastutilVersion
-    implementation "org.jetbrains.kotlinx:kotlinx-metadata-jvm:$kotlinExtMetadataJVMVersion"
-    implementation group: 'org.ow2.asm', name: 'asm', version: asmVersion
-    implementation group: 'org.ow2.asm', name: 'asm-commons', version: asmVersion
-    implementation group: 'org.ow2.asm', name: 'asm-tree', version: asmVersion
-    implementation group: 'org.ow2.asm', name: 'asm-analysis', version: asmVersion
-    implementation group: 'org.ow2.asm', name: 'asm-util', version: asmVersion
-
-    main17Implementation "com.google.code.gson:gson:$gsonVersion"
-    // Include all of guava when compiling the code, but exclude annotations that we don't
-    // need from the packaging.
-    main17CompileOnly("com.google.guava:guava:$guavaVersion")
-    main17Implementation("com.google.guava:guava:$guavaVersion", {
-        exclude group: 'com.google.errorprone'
-        exclude group: 'com.google.code.findbugs'
-        exclude group: 'com.google.j2objc'
-        exclude group: 'org.codehaus.mojo'
-    })
-    main17Implementation group: 'it.unimi.dsi', name: 'fastutil', version: fastutilVersion
-    main17Implementation "org.jetbrains.kotlinx:kotlinx-metadata-jvm:$kotlinExtMetadataJVMVersion"
-    main17Implementation group: 'org.ow2.asm', name: 'asm', version: asmVersion
-    main17Implementation group: 'org.ow2.asm', name: 'asm-commons', version: asmVersion
-    main17Implementation group: 'org.ow2.asm', name: 'asm-tree', version: asmVersion
-    main17Implementation group: 'org.ow2.asm', name: 'asm-analysis', version: asmVersion
-    main17Implementation group: 'org.ow2.asm', name: 'asm-util', version: asmVersion
-
-    testCompile "junit:junit:$junitVersion"
-    testCompile "com.google.guava:guava:$guavaVersion"
-    testCompile "org.jetbrains.kotlin:kotlin-stdlib:$kotlinVersion"
-    testCompile "org.jetbrains.kotlin:kotlin-reflect:$kotlinVersion"
-    testCompile group: 'com.android.tools.smali', name: 'smali', version: smaliVersion
-    testCompile files('third_party/jasmin/jasmin-2.4.jar')
-    testCompile files('third_party/jdwp-tests/apache-harmony-jdwp-tests-host.jar')
-    testCompile files('third_party/ddmlib/ddmlib.jar')
-    testCompile group: 'org.ow2.asm', name: 'asm', version: asmVersion
-    testCompile group: 'org.ow2.asm', name: 'asm-commons', version: asmVersion
-    testCompile group: 'org.ow2.asm', name: 'asm-tree', version: asmVersion
-    testCompile group: 'org.ow2.asm', name: 'asm-analysis', version: asmVersion
-    testCompile group: 'org.ow2.asm', name: 'asm-util', version: asmVersion
-    testCompile group: 'it.unimi.dsi', name: 'fastutil', version: fastutilVersion
-    testCompile group: 'org.javassist', name: 'javassist', version: javassistVersion
-
-    apiUsageSampleCompile sourceSets.main.output
-    apiUsageSampleCompile "com.google.guava:guava:$guavaVersion"
-    errorprone("com.google.errorprone:error_prone_core:$errorproneVersion")
-
-    keepannoCompile group: 'org.ow2.asm', name: 'asm', version: asmVersion
-    keepannoCompile "com.google.guava:guava:$guavaVersion"
-}
-
-def r8LibPath = "$buildDir/libs/r8lib.jar"
-def r8LibExludeDepsPath = "$buildDir/libs/r8lib-exclude-deps.jar"
-def r8DesugaredPath = "$buildDir/libs/r8desugared.jar"
-def r8LibGeneratedKeepRulesPath = "$buildDir/generated/keep.txt"
-def r8LibTestPath = "$buildDir/classes/r8libtest"
-def java11ClassFiles = "$buildDir/classes/java/mainJava11"
-def r8RetracePath = "$buildDir/libs/r8retrace.jar"
-def r8RetraceExludeDepsPath = "$buildDir/libs/r8retrace-exclude-deps.jar"
-
-def osString = OperatingSystem.current().isLinux() ? "linux" :
-        OperatingSystem.current().isMacOsX() ? "mac" : "windows"
-
-def cloudDependencies = [
-        "tests"      : [
-                "2017-10-04/art",
-                "2016-12-19/art"
-        ],
-        "third_party": [
-                "aapt2",
-                "android_cts_baseline",
-                "android_jar/libcore_latest",
-                "android_jar/lib-v14",
-                "android_jar/lib-v15",
-                "android_jar/lib-v19",
-                "android_jar/lib-v21",
-                "android_jar/lib-v22",
-                "android_jar/lib-v23",
-                "android_jar/lib-v24",
-                "android_jar/lib-v25",
-                "android_jar/lib-v26",
-                "android_jar/lib-v27",
-                "android_jar/lib-v28",
-                "android_jar/lib-v29",
-                "android_jar/lib-v30",
-                "android_jar/lib-v31",
-                "android_jar/lib-v32",
-                "android_jar/lib-v33",
-                "android_jar/lib-v34",
-                "android_jar/lib-master",
-                "api_database/api_database",
-                "api-outlining/simple-app-dump",
-                "binary_compatibility_tests/compiler_api_tests",
-                "bundletool/bundletool-1.11.0",
-                "core-lambda-stubs",
-                "dagger/2.41",
-                "dart-sdk",
-                "ddmlib",
-                "examples",
-                "examplesAndroidN",
-                "examplesAndroidO",
-                "examplesAndroidOLegacy",
-                "examplesAndroidOGenerated",
-                "examplesAndroidP",
-                "examplesAndroidPGenerated",
-                "gradle/gradle",
-                "google/google-java-format/1.14.0",
-                "google-java-format",
-                "gson/gson-2.10.1",
-                "guava/guava-32.1.2-android",
-                "guava/guava-32.1.2-jre",
-                "jacoco/0.8.2",
-                "jacoco/0.8.6",
-                "jasmin",
-                "junit",
-                "jdwp-tests",
-                "jsr223-api-1.0",
-                "rhino-1.7.10",
-                "rhino-android-1.1.1",
-                "kotlin/kotlin-compiler-1.3.72",
-                "kotlin/kotlin-compiler-1.4.20",
-                "kotlin/kotlin-compiler-1.5.0",
-                "kotlin/kotlin-compiler-1.6.0",
-                "kotlin/kotlin-compiler-1.7.0",
-                "kotlin/kotlin-compiler-1.8.0",
-                "kotlinx-coroutines-1.3.6",
-                "kotlinR8TestResources",
-                "multidex",
-                "openjdk/custom_conversion",
-                "openjdk/openjdk-rt-1.8",
-                "openjdk/desugar_jdk_libs",
-                "openjdk/desugar_jdk_libs_11",
-                "openjdk/desugar_jdk_libs_releases/1.0.9",
-                "openjdk/desugar_jdk_libs_releases/1.0.10",
-                "openjdk/desugar_jdk_libs_releases/1.1.0",
-                "openjdk/desugar_jdk_libs_releases/1.1.1",
-                "openjdk/desugar_jdk_libs_releases/1.1.5",
-                "openjdk/desugar_jdk_libs_releases/2.0.3",
-                "openjdk/jdk-11-test",
-                "opensource-apps/tivi",
-                "proguard/proguard5.2.1",
-                "proguard/proguard6.0.1",
-                "proguard/proguard-7.0.0",
-		"proguard/proguard-7.3.2",
-                "retrace_benchmark",
-                "retrace/binary_compatibility",
-                "r8",
-                "r8-releases/2.0.74",
-                "r8-releases/3.2.54",
-                "r8mappings",
-                "smali"
-        ],
-        // All dex-vms have a fixed OS of Linux, as they are only supported on Linux, and will be run in a Docker
-        // container on other platforms where supported.
-        "tools"      : [
-                "linux/art",
-                "linux/art-5.1.1",
-                "linux/art-6.0.1",
-                "linux/art-7.0.0",
-                "linux/art-8.1.0",
-                "linux/art-9.0.0",
-                "linux/art-10.0.0",
-                "linux/host/art-12.0.0-beta4",
-                "linux/host/art-13.0.0",
-                "linux/host/art-14.0.0-beta3",
-                "linux/host/art-master",
-                "linux/dalvik",
-                "linux/dalvik-4.0.4",
-        ]
-]
-
-def cloudSystemDependencies = [
-        linux: [
-                "third_party": ["openjdk/openjdk-9.0.4/linux",
-                                "openjdk/jdk8/linux-x86",
-                                "openjdk/jdk-11/linux",
-                                "openjdk/jdk-17/linux",
-                                "openjdk/jdk-20/linux"],
-        ],
-        osx: [
-                "third_party": ["openjdk/openjdk-9.0.4/osx",
-                                "openjdk/jdk8/darwin-x86",
-                                "openjdk/jdk-11/osx",
-                                "openjdk/jdk-17/osx",
-                                "openjdk/jdk-20/osx"],
-        ],
-        windows: [
-                "third_party": ["openjdk/openjdk-9.0.4/windows",
-                                "openjdk/jdk-11/windows",
-                                "openjdk/jdk-17/windows",
-                                "openjdk/jdk-20/windows"],
-        ],
-]
-
-if (OperatingSystem.current().isWindows()) {
-    cloudSystemDependencies.windows.each { entry ->
-        cloudDependencies.get(entry.key).addAll(entry.value)
-    }
-} else if (OperatingSystem.current().isLinux()) {
-    cloudSystemDependencies.linux.each { entry ->
-        cloudDependencies.get(entry.key).addAll(entry.value)
-    }
-} else if (OperatingSystem.current().isMacOsX()) {
-    cloudSystemDependencies.osx.each { entry ->
-        cloudDependencies.get(entry.key).addAll(entry.value)
-    }
-} else {
-    println "WARNING: Unsupported system: " + OperatingSystem.current()
-}
-
-def getDownloadDepsTaskName(entryKey, entryFile) {
-    return "download_deps_${entryKey}_${entryFile.replace('/', '_').replace('\\', '_')}"
-}
-
-cloudDependencies.each { entry ->
-    entry.value.each { entryFile ->
-        task (getDownloadDepsTaskName(entry.key, entryFile), type: DownloadDependency) {
-            type DownloadDependency.Type.GOOGLE_STORAGE
-            dependency "${entry.key}/${entryFile}"
-        }
-    }
-}
-
-def x20Dependencies = [
-    "third_party": [
-        "benchmarks/kotlin-benches",
-        "chrome/chrome_200430",
-        "chrome/monochrome_public_minimal_apks/chrome_200520",
-        "chrome/clank_google3_prebuilt",
-        "classlib",
-        "cf_segments",
-        "desugar/desugar_20180308",
-        "internal/issue-127524985",
-        "framework",
-        "gmail/gmail_android_180826.15",
-        "gmscore/gmscore_v10",
-        "gmscore/latest",
-        "nest/nest_20180926_7c6cfb",
-        "proguard/proguard_internal_159423826",
-        "proguardsettings",
-        "proto",
-        "protobuf-lite",
-        "retrace_internal",
-        "youtube/youtube.android_17.19"
-    ],
-]
-
-x20Dependencies.each { entry ->
-    entry.value.each { entryFile ->
-        task "${getDownloadDepsTaskName(entry.key, entryFile)}"(type: DownloadDependency) {
-            type DownloadDependency.Type.X20
-            dependency "${entry.key}/${entryFile}"
-        }
-    }
-}
-
-task downloadOpenJDKrt {
-   cloudDependencies.each { entry ->
-        entry.value.each { entryFile ->
-            if (entryFile.contains("openjdk-rt")) {
-                dependsOn "${getDownloadDepsTaskName(entry.key, entryFile)}"
-            }
-        }
-    }
-}
-
-task downloadAndroidCts {
-    cloudDependencies.each { entry ->
-        entry.value.each { entryFile ->
-            if (entryFile.contains("android_cts_baseline")) {
-                dependsOn "${getDownloadDepsTaskName(entry.key, entryFile)}"
-            }
-        }
-    }
-}
-
-task downloadCloudDeps() {
-    cloudDependencies.each { entry ->
-        entry.value.each { entryFile ->
-            dependsOn "${getDownloadDepsTaskName(entry.key, entryFile)}"
-        }
-    }
-}
-
-task downloadX20Deps() {
-    x20Dependencies.each { entry ->
-        entry.value.each { entryFile ->
-            dependsOn "${getDownloadDepsTaskName(entry.key, entryFile)}"
-        }
-    }
-}
-
-task downloadDeps {
-    dependsOn downloadCloudDeps
-    if (!project.hasProperty('no_internal')) {
-        dependsOn downloadX20Deps
-    }
-}
-
-allprojects {
-    sourceCompatibility = JavaVersion.VERSION_1_8
-    targetCompatibility = JavaVersion.VERSION_1_8
-}
-
-// TODO(ricow): Remove debug prints
-println("NOTE: Current operating system: " + OperatingSystem.current())
-println("NOTE: Current operating system isWindows: " + OperatingSystem.current().isWindows())
-
-// Check if running with the JDK location from tools/jdk.py.
-if (OperatingSystem.current().isWindows()) {
-    println "NOTE: Running with JDK: " + org.gradle.internal.jvm.Jvm.current().javaHome
-    compileJava.options.encoding = "UTF-8"
-    compileTestJava.options.encoding = "UTF-8"
-} else {
-    def javaHomeOut = new StringBuilder()
-    def javaHomeErr = new StringBuilder()
-    def javaHomeProc = './tools/jdk.py'.execute([], projectDir)
-    javaHomeProc.waitForProcessOutput(javaHomeOut, javaHomeErr)
-    def jdkHome = new File(javaHomeOut.toString().trim())
-    if (!jdkHome.exists()) {
-        println "WARNING: Failed to find the ./tools/jdk.py specified JDK: " + jdkHome
-    } else if (jdkHome != org.gradle.internal.jvm.Jvm.current().javaHome) {
-        println("WARNING: Gradle is running in a non-pinned Java"
-                + ". Gradle Java Home: " + org.gradle.internal.jvm.Jvm.current().javaHome
-                + ". Expected: " + jdkHome)
-    } else {
-        println("NOTE: Running with jdk from tools/jdk.py: " + jdkHome)
-    }
-}
-
-compileJava.dependsOn downloadCloudDeps
-
-sourceSets.configureEach { sourceSet ->
-    tasks.named(sourceSet.compileJavaTaskName).configure {
-        // Default disable errorprone (enabled and setup below).
-        options.errorprone.enabled = false
-        options.compilerArgs << '-Xlint:unchecked'
-        // Run all compilation tasks in a forked subprocess.
-        options.fork = true
-        // Javac often runs out of stack space when compiling the tests.
-        // Increase the stack size for the javac process.
-        options.forkOptions.jvmArgs << "-Xss256m"
-        // Test compilation is sometimes hitting the default limit at 1g, increase it.
-        options.forkOptions.jvmArgs << "-Xmx3g"
-    }
-}
-
-def setJdkCompilationWithCompatibility(String sourceSet, String javaHome, JavaVersion compatibility, boolean enablePreview) {
-    tasks.named(sourceSet).get().configure {
-        def jdkDir = "third_party/openjdk/${javaHome}/"
-        options.fork = true
-        options.forkOptions.jvmArgs = []
-        if (enablePreview) {
-            options.compilerArgs.add('--enable-preview')
-        }
-        if (OperatingSystem.current().isLinux()) {
-            dependsOn getDownloadDepsTaskName("third_party", "openjdk/" + javaHome + "/linux")
-            options.forkOptions.javaHome = file(jdkDir + 'linux')
-        } else if (OperatingSystem.current().isMacOsX()) {
-            dependsOn getDownloadDepsTaskName("third_party", "openjdk/" + javaHome + "/osx")
-            options.forkOptions.javaHome = compatibility > JavaVersion.VERSION_1_9
-                    ? file(jdkDir + 'osx/Contents/Home')
-                    : file(jdkDir + 'osx')
-        } else {
-            dependsOn getDownloadDepsTaskName("third_party", "openjdk/" + javaHome + "/windows")
-            options.forkOptions.javaHome = file(jdkDir + 'windows')
-        }
-        sourceCompatibility = compatibility
-        targetCompatibility = compatibility
-    }
-}
-
-setJdkCompilationWithCompatibility(
-        sourceSets.main.compileJavaTaskName,
-        'jdk-11',
-        JavaVersion.VERSION_11,
-        false);
-
-setJdkCompilationWithCompatibility(
-        sourceSets.examplesJava9.compileJavaTaskName,
-        'openjdk-9.0.4',
-        JavaVersion.VERSION_1_9,
-        false)
-setJdkCompilationWithCompatibility(
-        sourceSets.examplesJava10.compileJavaTaskName,
-        'jdk-11',
-        JavaVersion.VERSION_1_10,
-        false)
-setJdkCompilationWithCompatibility(
-        sourceSets.main17.compileJavaTaskName,
-        'jdk-17',
-        JavaVersion.VERSION_17,
-        false)
-setJdkCompilationWithCompatibility(
-        sourceSets.examplesJava11.compileJavaTaskName,
-        'jdk-11',
-        JavaVersion.VERSION_11,
-        false)
-setJdkCompilationWithCompatibility(
-        sourceSets.examplesJava17.compileJavaTaskName,
-        'jdk-17',
-        JavaVersion.VERSION_17,
-        false)
-setJdkCompilationWithCompatibility(
-        sourceSets.examplesJava20.compileJavaTaskName,
-        'jdk-20',
-        // TODO(b/218293990): Update Gradle to get JavaVersion.VERSION_18.
-        JavaVersion.VERSION_17,
-        false)
-
-if (!project.hasProperty('without_error_prone') &&
-        // Don't enable error prone on Java 8 as the plugin setup does not support it.
-        !org.gradle.internal.jvm.Jvm.current().javaVersion.java8) {
-    compileJava {
-
-        // Enable error prone for D8/R8 main sources.
-        options.errorprone.enabled = true
-
-        // Make all warnings errors. Warnings that we have chosen not to fix (or suppress) are
-        // disabled outright below.
-        options.compilerArgs << "-Werror"
-
-        // Increase number of reported errors to 1000 (default is 100).
-        options.compilerArgs << "-Xmaxerrs"
-        options.compilerArgs << "1000"
-
-        // Non-default / Experimental checks - explicitly enforced.
-        options.errorprone.check('RemoveUnusedImports', CheckSeverity.ERROR)
-        options.errorprone.check('InconsistentOverloads', CheckSeverity.ERROR)
-        options.errorprone.check('MissingDefault', CheckSeverity.ERROR)
-        options.errorprone.check('MultipleTopLevelClasses', CheckSeverity.ERROR)
-        options.errorprone.check('NarrowingCompoundAssignment', CheckSeverity.ERROR)
-
-        // Warnings that cause unwanted edits (e.g., inability to write informative asserts).
-        options.errorprone.check('AlreadyChecked', CheckSeverity.OFF)
-
-        // JavaDoc related warnings. Would be nice to resolve but of no real consequence.
-        options.errorprone.check('InvalidLink', CheckSeverity.OFF)
-        options.errorprone.check('InvalidBlockTag', CheckSeverity.OFF)
-        options.errorprone.check('InvalidInlineTag', CheckSeverity.OFF)
-        options.errorprone.check('EmptyBlockTag', CheckSeverity.OFF)
-        options.errorprone.check('MissingSummary', CheckSeverity.OFF)
-        options.errorprone.check('UnrecognisedJavadocTag', CheckSeverity.OFF)
-        options.errorprone.check('AlmostJavadoc', CheckSeverity.OFF)
-
-        // Moving away from identity and canonical items is not planned.
-        options.errorprone.check('IdentityHashMapUsage', CheckSeverity.OFF)
-    }
-}
-
-task consolidatedLicense {
-    def license = new File(new File(buildDir, 'generatedLicense'), 'LICENSE')
-
-    inputs.files files('LICENSE', 'LIBRARY-LICENSE') + fileTree(dir: 'library-licensing')
-    def runtimeClasspath = configurations.findByName("runtimeClasspath")
-    inputs.files { runtimeClasspath.getResolvedConfiguration().files }
-
-    outputs.files license
-
-    doLast {
-        def dependencies = []
-        runtimeClasspath.resolvedConfiguration.resolvedArtifacts.each {
-            def identifier = (ModuleComponentIdentifier) it.id.componentIdentifier
-            dependencies.add("${identifier.group}:${identifier.module}")
-        }
-        def libraryLicenses = file('LIBRARY-LICENSE').text
-        dependencies.each {
-            if (!libraryLicenses.contains("- artifact: $it")) {
-                 throw new GradleException("No license for $it in LIBRARY_LICENSE")
-            }
-        }
-
-        license.getParentFile().mkdirs()
-        license.createNewFile()
-        license.text = "This file lists all licenses for code distributed.\n"
-        license.text += "All non-library code has the following 3-Clause BSD license.\n"
-        license.text += "\n"
-        license.text += "\n"
-        license.text += file('LICENSE').text
-        license.text += "\n"
-        license.text += "\n"
-        license.text += "Summary of distributed libraries:\n"
-        license.text += "\n"
-        license.text += libraryLicenses
-        license.text += "\n"
-        license.text += "\n"
-        license.text += "Licenses details:\n"
-        fileTree(dir: 'library-licensing').getFiles().stream().sorted().forEach { file ->
-            license.text += "\n"
-            license.text += "\n"
-            license.text += file.text
-        }
-    }
-}
-
-def repackageDepFile(file) {
-    if (file.getName().endsWith('.jar')) {
-        return zipTree(file).matching {
-            exclude '**/module-info.class'
-            exclude 'META-INF/maven/**'
-            exclude 'META-INF/LICENSE.txt'
-            exclude 'META-INF/MANIFEST.MF'
-        }
-    } else {
-        return fileTree(file)
-    }
-}
-
-task repackageDeps(type: Jar) {
-    dependsOn downloadCloudDeps
-    dependsOn project.configurations.runtimeClasspath
-    project.configurations.runtimeClasspath.forEach {
-        from repackageDepFile(it)
-    }
-    archiveFileName = 'deps_all.jar'
-}
-
-task repackageTestDeps(type: Jar) {
-    dependsOn downloadCloudDeps
-    dependsOn project.configurations.testCompile
-    project.configurations.testCompile.forEach {
-        from repackageDepFile(it)
-    }
-    archiveFileName = 'test_deps_all.jar'
-}
-
-task repackageSources(type: Jar) {
-    // If this fails then remove all generated folders from
-    // build/classes/java/test that is not {com,dalvik}
-    from sourceSets.main.output
-    archiveFileName = 'sources_main.jar'
-}
-
-task repackageSources17(type: Jar) {
-    from sourceSets.main17.output
-    archiveFileName = 'sources_main_17.jar'
-}
-
-def r8CreateTask(name, baseName, sources, includeLibraryLicenses, includeSwissArmyKnife) {
-    return tasks.create("r8Create${name}", Jar) {
-        entryCompression ZipEntryCompression.STORED
-        dependsOn sources
-        dependsOn files('LICENSE')
-        if (includeLibraryLicenses) {
-            from consolidatedLicense.outputs.files
-        } else {
-            from files('LICENSE')
-        }
-        from sources.collect { zipTree(it) }
-        exclude "$buildDir/classes/**"
-        archiveFileName = baseName
-        if (includeSwissArmyKnife) {
-            manifest {
-                attributes 'Main-Class': 'com.android.tools.r8.SwissArmyKnife'
-            }
-        }
-        exclude "META-INF/*.kotlin_module"
-        exclude "**/*.kotlin_metadata"
-    }
-}
-
-def r8RelocateTask(r8Task, output) {
-    return tasks.create("r8Relocate_${r8Task.name}", Exec) {
-        dependsOn r8WithDeps
-        dependsOn r8Task
-        outputs.file output
-        workingDir = projectDir
-        inputs.files r8Task.outputs.files + r8WithDeps.outputs.files
-        commandLine baseCompilerCommandLine([
-                "relocator",
-                "--input",
-                r8Task.outputs.files[0],
-                "--output",
-                output,
-                "--map",
-                "com.google.common.**->com.android.tools.r8.com.google.common",
-                "--map",
-                "com.google.gson.**->com.android.tools.r8.com.google.gson",
-                "--map",
-                "com.google.thirdparty.**->com.android.tools.r8.com.google.thirdparty",
-                "--map",
-                "org.objectweb.asm.**->com.android.tools.r8.org.objectweb.asm",
-                "--map",
-                "it.unimi.dsi.fastutil.**->com.android.tools.r8.it.unimi.dsi.fastutil",
-                "--map",
-                "kotlin.**->com.android.tools.r8.jetbrains.kotlin",
-                "--map",
-                "kotlinx.**->com.android.tools.r8.jetbrains.kotlinx",
-                "--map",
-                "org.jetbrains.**->com.android.tools.r8.org.jetbrains",
-                "--map",
-                "org.intellij.**->com.android.tools.r8.org.intellij",
-                "--map",
-                "org.checkerframework.**->com.android.tools.r8.org.checkerframework"
-        ])
-    }
-}
-
-task r8WithDeps {
-    dependsOn repackageSources
-    dependsOn repackageDeps
-    inputs.files ([repackageSources.outputs, repackageDeps.outputs])
-    def r8Task = r8CreateTask(
-            'WithDeps',
-            'r8_with_deps.jar',
-            repackageSources.outputs.files + repackageDeps.outputs.files,
-            true,
-            true)
-    dependsOn r8Task
-    outputs.files r8Task.outputs.files
-}
-
-task r8WithDeps17 {
-    dependsOn repackageSources17
-    dependsOn repackageDeps
-    inputs.files ([repackageSources17.outputs, repackageDeps.outputs])
-    def r8Task = r8CreateTask(
-            'WithDeps17',
-            'r8_with_deps_17.jar',
-            repackageSources17.outputs.files + repackageDeps.outputs.files,
-            true,
-            true)
-    dependsOn r8Task
-    outputs.files r8Task.outputs.files
-}
-
-task r8WithRelocatedDeps {
-    def output = "${buildDir}/libs/r8_with_relocated_deps.jar"
-    dependsOn r8RelocateTask(r8WithDeps, output)
-    inputs.files r8WithDeps.outputs.files
-    outputs.file output
-}
-
-task r8WithRelocatedDeps17 {
-    def output = "${buildDir}/libs/r8_with_relocated_deps_17.jar"
-    dependsOn r8RelocateTask(r8WithDeps17, output)
-    inputs.files r8WithDeps17.outputs.files
-    outputs.file output
-}
-
-task r8WithoutDeps {
-    dependsOn repackageSources
-    inputs.files repackageSources.outputs
-    def r8Task = r8CreateTask(
-            'WithoutDeps',
-            'r8_without_deps.jar',
-            repackageSources.outputs.files,
-            false,
-            true)
-    dependsOn r8Task
-    outputs.files r8Task.outputs.files
-}
-
-task r8(type: Copy) {
-    def r8Task = project.hasProperty("exclude_deps")
-            ? r8WithoutDeps : r8WithRelocatedDeps
-    dependsOn r8Task
-    from r8Task.outputs.files[0]
-    into file("${buildDir}/libs")
-    rename { String fileName -> "r8.jar" }
-    outputs.file "${buildDir}/libs/r8.jar"
-}
-
-task r8NoManifestWithoutDeps {
-    dependsOn repackageSources
-    inputs.files repackageSources.outputs
-    def r8Task = r8CreateTask(
-            'NoManifestWithoutDeps',
-            'r8_no_manifest_without_deps.jar',
-            repackageSources.outputs.files,
-            false,
-            false)
-    dependsOn r8Task
-    outputs.files r8Task.outputs.files
-}
-
-task r8NoManifestWithDeps {
-    dependsOn repackageSources
-    inputs.files ([repackageSources.outputs, repackageDeps.outputs])
-    def r8Task = r8CreateTask(
-            'NoManifestWithDeps',
-            'r8_no_manifest_with_deps.jar',
-            repackageSources.outputs.files + repackageDeps.outputs.files,
-            true,
-            false)
-    dependsOn r8Task
-    outputs.files r8Task.outputs.files
-}
-
-task r8NoManifestWithRelocatedDeps {
-    def output = "${buildDir}/libs/r8_no_manifest_with_relocated_deps.jar"
-    dependsOn r8RelocateTask(r8NoManifestWithDeps, output)
-    inputs.files r8NoManifestWithDeps.outputs.files
-    outputs.file output
-}
-
-task r8NoManifest(type: Copy) {
-    def r8Task = project.hasProperty("exclude_deps")
-            ? r8NoManifestWithoutDeps : r8NoManifestWithRelocatedDeps
-    dependsOn r8Task
-    from r8Task.outputs.files[0]
-    into file("${buildDir}/libs")
-    rename { String fileName -> "r8_no_manifest.jar" }
-    outputs.file "${buildDir}/libs/r8_no_manifest.jar"
-}
-
-def baseCompilerCommandLine(compiler, args = []) {
-    // Execute r8 commands against a stable r8 with dependencies.
-    // TODO(b/139725780): See if we can remove or lower the heap size (-Xmx8g).
-    return [org.gradle.internal.jvm.Jvm.current().getJavaExecutable(),
-            "-Xmx8g", "-ea", "-jar", r8WithDeps.outputs.files[0]] + compiler + args
-}
-
-def baseR8CommandLine(args = []) {
-    // Execute r8 commands against a stable r8 with dependencies.
-    return baseCompilerCommandLine("r8", args)
-}
-
-def baseD8CommandLine(args = []) {
-    // Execute r8 commands against a stable r8 with dependencies.
-    return baseCompilerCommandLine("d8", args)
-}
-
-def r8CfCommandLine(input, output, pgConfs = [], args = ["--release"], libs = []) {
-    def allArgs = [
-            "--classfile",
-            input,
-            "--output", output,
-            "--pg-map-output", output + ".map",
-            "--partition-map-output", output + "_map.zip",
-            "--lib", org.gradle.internal.jvm.Jvm.current().javaHome,
-    ] + args + libs.collectMany { ["--lib", it] } + pgConfs.collectMany { ["--pg-conf", it] }
-    return baseR8CommandLine(allArgs)
-}
-
-def d8CfCommandLine(input, output, args = ["--release"], libs = []) {
-    def allArgs = [
-            "--classfile",
-            input,
-            "--output", output,
-            "--lib", "third_party/openjdk/openjdk-rt-1.8/rt.jar"
-    ] + args + libs.collectMany { ["--lib", it] }
-    return baseD8CommandLine(allArgs)
-}
-
-def r8LibCreateTask(
-    name, pgConfs = [], r8Task, output, libs = [], classpath = [], excldeps=false, debug=false) {
-    return tasks.create("r8Lib${name}", Exec) {
-        inputs.files ([pgConfs, r8WithRelocatedDeps.outputs, r8Task.outputs])
-        outputs.file output
-        dependsOn downloadOpenJDKrt
-        dependsOn r8WithRelocatedDeps
-        dependsOn r8Task
-        commandLine ([
-                "python3", "tools/create_r8lib.py",
-                "--r8jar", r8Task.outputs.files[0],
-                "--output", output]
-                + (excldeps ? ['--excldeps-variant'] : [])
-                + (debug ? ['--debug-variant'] : [])
-                + (pgConfs.collectMany { ["--pg-conf", it] })
-                + (libs.collectMany { ["--lib", it] })
-                + (classpath.collectMany { ["--classpath", it] }))
-        workingDir = projectDir
-    }
-}
-
-task testJarSources(type: Jar, dependsOn: [testClasses]) {
-    archiveFileName = "r8testsbase.jar"
-    from sourceSets.test.output
-    // We only want to include tests that use R8 when generating keep rules for applymapping.
-    include "com/android/tools/r8/**"
-    include "android/**"
-    include "dalvik/**"
-}
-
-task testJar(type: Exec) {
-    dependsOn r8WithDeps
-    dependsOn testJarSources
-    def output = "$buildDir/libs/r8tests.jar"
-    outputs.file output
-    workingDir = projectDir
-    inputs.files (testJarSources.outputs.files + r8WithDeps.outputs.files)
-    commandLine baseCompilerCommandLine([
-            "relocator",
-            "--input",
-            testJarSources.outputs.files[0],
-            "--output",
-            output,
-            "--map",
-            "kotlinx.metadata.**->com.android.tools.r8.jetbrains.kotlinx.metadata"
-    ])
-}
-
-task generateR8LibKeepRules(type: Exec) {
-    // Depend on r8WithRelocatedDeps to ensure that we do not have external
-    // dependencies crossing the boundary.
-    dependsOn r8WithDeps
-    dependsOn r8NoManifestWithRelocatedDeps
-    dependsOn testJar
-    dependsOn repackageTestDeps
-    dependsOn downloadOpenJDKrt
-    inputs.files ([
-            r8WithDeps.outputs,
-            r8NoManifestWithRelocatedDeps.outputs,
-            repackageDeps.outputs,
-            repackageTestDeps.outputs,
-            testJar.outputs])
-    outputs.file r8LibGeneratedKeepRulesPath
-    commandLine baseCompilerCommandLine([
-            "tracereferences",
-            "--keep-rules",
-            "--allowobfuscation",
-            "--lib",
-            "third_party/openjdk/openjdk-rt-1.8/rt.jar",
-            "--lib",
-            repackageDeps.outputs.files[0],
-            "--lib",
-            repackageTestDeps.outputs.files[0],
-            "--target",
-            r8NoManifestWithRelocatedDeps.outputs.files[0],
-            "--source",
-            testJar.outputs.files[0],
-            "--output",
-            r8LibGeneratedKeepRulesPath])
-    workingDir = projectDir
-}
-
-task R8Lib {
-    dependsOn r8LibCreateTask(
-            "Main",
-            ["src/main/keep.txt", generateR8LibKeepRules.outputs.files[0]],
-            r8NoManifestWithRelocatedDeps,
-            r8LibPath
-    ).dependsOn(generateR8LibKeepRules)
-    inputs.files r8NoManifestWithRelocatedDeps.outputs.files
-    outputs.file r8LibPath
-}
-
-task R8LibNoDeps {
-    dependsOn r8LibCreateTask(
-            "MainNoDeps",
-            ["src/main/keep.txt"],
-            r8NoManifestWithoutDeps,
-            r8LibExludeDepsPath,
-            [],
-            repackageDeps.outputs.files,
-            true,
-    ).dependsOn(repackageDeps)
-    inputs.files ([r8NoManifestWithoutDeps.outputs, repackageDeps.outputs])
-    outputs.file r8LibExludeDepsPath
-}
-
-task R8Desugared(type: Exec) {
-    dependsOn downloadOpenJDKrt
-    dependsOn r8NoManifestWithRelocatedDeps
-    inputs.files r8NoManifestWithRelocatedDeps.outputs.files
-    commandLine d8CfCommandLine(
-            r8NoManifestWithRelocatedDeps.outputs.files[0],
-            r8DesugaredPath,
-            ["--release"])
-    workingDir = projectDir
-    outputs.file r8DesugaredPath
-}
-
-task R8Retrace {
-    dependsOn R8Lib
-    dependsOn r8LibCreateTask(
-            "Retrace",
-            ["src/main/keep_retrace.txt"],
-            R8Lib,
-            r8RetracePath,
-            [],
-            [],
-            false,
-            true
-    ).dependsOn(R8Lib)
-    outputs.file r8RetracePath
-}
-
-task R8RetraceNoDeps {
-    dependsOn R8LibNoDeps
-    dependsOn r8LibCreateTask(
-            "RetraceNoDeps",
-            ["src/main/keep_retrace.txt"],
-            R8LibNoDeps,
-            r8RetraceExludeDepsPath,
-            [],
-            repackageDeps.outputs.files,
-            true,
-            true,
-    ).dependsOn(R8LibNoDeps)
-    outputs.file r8RetraceExludeDepsPath
-}
-
-task sourceJar(type: Jar, dependsOn: classes) {
-    classifier = 'src'
-    from sourceSets.main.allSource
-}
-
-task keepAnnoJar(type: Jar) {
-    archiveFileName = "keepanno-annotations.jar"
-    from sourceSets.keepanno.output
-}
-
-artifacts {
-    archives sourceJar
-}
-
-task createArtTests(type: Exec) {
-    def outputDir = "build/generated/test/java/com/android/tools/r8/art"
-    def createArtTestsScript = "tools/create_art_tests.py"
-    inputs.files files("tests/2017-10-04/art.tar.gz", createArtTestsScript)
-    outputs.dir outputDir
-    dependsOn downloadDeps
-    commandLine "python3", createArtTestsScript
-    workingDir = projectDir
-}
-
-compileTestJava {
-    dependsOn createArtTests
-}
-
-task buildCfSegments(type: Jar, dependsOn: downloadDeps) {
-    from sourceSets.cfSegments.output
-    archiveFileName = 'cf_segments.jar'
-    destinationDir file('build/libs')
-}
-
-task buildR8ApiUsageSample(type: Jar) {
-    from sourceSets.apiUsageSample.output
-    archiveFileName = 'r8_api_usage_sample.jar'
-    destinationDir file('tests')
-}
-
-task buildApiSampleJars {
-    dependsOn buildR8ApiUsageSample
-}
-
-def buildExampleJarsCreateTask(javaVersion, sourceSet) {
-    return tasks.create("buildExample${javaVersion}Jars") {
-        def examplesDir = file("src/test/examples${javaVersion}")
-        examplesDir.eachDir { dir ->
-            def name = dir.getName();
-            def exampleOutputDir = file("build/test/examples${javaVersion}");
-            def jarName = "${name}.jar"
-            dependsOn "jar_examples${javaVersion}_${name}"
-            task "jar_examples${javaVersion}_${name}"(type: Jar) {
-                archiveName = jarName
-                destinationDir = exampleOutputDir
-                from sourceSet.output
-                include "**/" + name + "/**/*.class"
-            }
-        }
-    }
-}
-
-buildExampleJarsCreateTask("Java9", sourceSets.examplesJava9)
-buildExampleJarsCreateTask("Java10", sourceSets.examplesJava10)
-buildExampleJarsCreateTask("Java11", sourceSets.examplesJava11)
-buildExampleJarsCreateTask("Java17", sourceSets.examplesJava17)
-buildExampleJarsCreateTask("Java20", sourceSets.examplesJava20)
-
-task buildExamples {
-    if (OperatingSystem.current().isMacOsX() || OperatingSystem.current().isWindows()) {
-        logger.lifecycle("WARNING: Testing (including building examples) is only partially supported on your " +
-                "platform (" + OperatingSystem.current().getName() + ").")
-    } else if (!OperatingSystem.current().isLinux()) {
-      logger.lifecycle("WARNING: Testing (including building examples) is not supported on your platform. " +
-          "It is fully supported on Linux and partially supported on Mac OS and Windows")
-      return;
-    }
-    dependsOn buildExampleJava9Jars
-    dependsOn buildExampleJava10Jars
-    dependsOn buildExampleJava11Jars
-    dependsOn buildExampleJava17Jars
-    dependsOn buildExampleJava20Jars
-}
-
-tasks.withType(Test) {
-    println("NOTE: Number of processors " + Runtime.runtime.availableProcessors())
-    def userDefinedCoresPerFork = System.getenv('R8_GRADLE_CORES_PER_FORK')
-    def processors = Runtime.runtime.availableProcessors()
-    // See https://docs.gradle.org/current/dsl/org.gradle.api.tasks.testing.Test.html.
-    if (userDefinedCoresPerFork) {
-      maxParallelForks = processors.intdiv(userDefinedCoresPerFork.toInteger()) ?: 1
-    } else {
-      // On normal work machines this seems to give the best test execution time (without freezing)
-      maxParallelForks = processors.intdiv(3) ?: 1
-      // On low cpu count machines (bots) we under subscribe, so increase the count.
-      if (processors == 32) {
-        maxParallelForks = 15
-      }
-    }
-    println("NOTE: Max parallel forks " + maxParallelForks)
-
-    forkEvery = 0
-    if (project.hasProperty('disable_assertions')) {
-        enableAssertions = false
-    }
-    // TODO(b/124091860): Increase the max heap size to avoid OOM when running tests.
-    if (project.hasProperty('test_xmx')) {
-      maxHeapSize = project.property('test_xmx')
-    } else {
-      maxHeapSize = "4G"
-    }
-}
-
-task generateR8TestKeepRules {
-    def path = "build/generated/r8tests-keep.txt"
-    outputs.file path
-    dependsOn R8Lib
-    doLast {
-        file(path).write """-keep class ** { *; }
--dontshrink
--dontoptimize
--keepattributes *
--applymapping ${R8Lib.outputs.files[0]}.map
-"""
-    }
-}
-
-task buildR8LibCfTestDeps(type: Exec) {
-    def outputPath = "build/libs/r8libtestdeps-cf.jar"
-    dependsOn downloadDeps
-    dependsOn r8NoManifest
-    dependsOn R8Lib
-    dependsOn generateR8TestKeepRules
-    dependsOn testJar
-    // Take all .jar files as libraries and append the generated test classes in classes/java/test.
-    def addedLibraries = sourceSets.test.runtimeClasspath.findAll { pkg ->
-        return pkg.toString().endsWith(".jar")
-    } + ["${buildDir}/classes/java/test"]
-    inputs.files testJar.outputs.files +
-            generateR8TestKeepRules.outputs.files +
-            R8Lib.outputs
-    commandLine = r8CfCommandLine(
-            testJar.outputs.files[0],
-            outputPath,
-            [generateR8TestKeepRules.outputs.files[0]],
-            ["--debug", "--classpath", r8NoManifest.outputs.files[0]],
-            r8NoManifest.outputs.files + addedLibraries)
-    workingDir = projectDir
-    outputs.file outputPath
-}
-
-task configureTestForR8Lib(type: Copy) {
-    dependsOn testJar
-    inputs.files buildR8LibCfTestDeps.outputs
-    dependsOn R8Lib
-    delete r8LibTestPath
-    from zipTree(buildR8LibCfTestDeps.outputs.files[0])
-    def examplesDir = file("build/test")
-    if (examplesDir.exists()) {
-        examplesDir.eachDir { dir ->
-            from ("${buildDir}/test/${dir.getName()}/classes")
-        }
-    }
-    from ("${buildDir}/runtime/examples")
-    into r8LibTestPath
-    outputs.dir r8LibTestPath
-}
-
-def shouldRetrace() {
-    return project.hasProperty('r8lib') || project.hasProperty('r8lib_no_deps')
-}
-
-def retrace(Throwable exception) {
-    def out = new StringBuffer()
-    def err = new StringBuffer()
-    def command = "python3 tools/retrace.py --quiet"
-    def header = "RETRACED STACKTRACE";
-    out.append("\n--------------------------------------\n")
-    out.append("${header}\n")
-    out.append("--------------------------------------\n")
-    Process process = command.execute()
-    def processIn = new PrintStream(process.getOut())
-    process.consumeProcessOutput(out, err)
-    exception.printStackTrace(processIn)
-    processIn.flush()
-    processIn.close()
-    def errorDuringRetracing = process.waitFor() != 0
-    if (errorDuringRetracing) {
-        out.append("ERROR DURING RETRACING\n")
-        out.append(err.toString())
-    }
-    if (project.hasProperty('print_obfuscated_stacktraces') || errorDuringRetracing) {
-        out.append("\n\n--------------------------------------\n")
-        out.append("OBFUSCATED STACKTRACE\n")
-        out.append("--------------------------------------\n")
-    }
-    return out.toString()
-}
-
-def printStackTrace(TestResult result) {
-    filterStackTraces(result)
-    if (shouldRetrace()) {
-        def exception = new Exception(retrace(result.exception))
-        exception.setStackTrace([] as StackTraceElement[])
-        result.exceptions.add(0, exception)
-    }
-}
-
-def filterStackTraces(TestResult result) {
-    for (Throwable throwable : result.getExceptions()) {
-        filterStackTrace(throwable)
-    }
-}
-
-// It would be nice to do this in a non-destructive way...
-def filterStackTrace(Throwable exception) {
-    if (!project.hasProperty('print_full_stacktraces')) {
-        def elements = []
-        def skipped = []
-        for (StackTraceElement element : exception.getStackTrace()) {
-            if (element.toString().contains("com.android.tools.r8")) {
-                elements.addAll(skipped)
-                elements.add(element)
-                skipped.clear()
-            } else {
-                skipped.add(element)
-            }
-        }
-        exception.setStackTrace(elements as StackTraceElement[])
-    }
-}
-
-def printAllStackTracesToFile(List<Throwable> exceptions, File out) {
-    new PrintStream(new FileOutputStream(out)).withCloseable {printer ->
-        exceptions.forEach { it.printStackTrace(printer) }
-    }
-}
-
-static def escapeHtml(String string) {
-    return string.replace("&", "&amp;").replace("<", "&lt;").replace(">", "&gt;")
-}
-
-static def urlEncode(String string) {
-    // Not sure why, but the + also needs to be converted to have working links.
-    return URLEncoder.encode(string, "UTF-8").replace("+","%20")
-}
-
-def ensureDir(File dir) {
-    dir.mkdirs()
-    return dir
-}
-
-// Some of our test parameters have new lines :-( We really don't want test names to span lines.
-static def sanitizedTestName(testDesc) {
-    if (testDesc.getName().contains("\n")) {
-        throw new RuntimeException("Unsupported use of newline in test name: '${testDesc.getName()}'")
-    }
-    return testDesc.getName()
-}
-
-static def desanitizedTestName(testName) {
-    return testName
-}
-
-def getTestReportEntryDir(reportDir, testDesc) {
-    return ensureDir(reportDir.toPath()
-            .resolve(testDesc.getClassName())
-            .resolve(sanitizedTestName(testDesc))
-            .toFile())
-}
-
-def getTestReportEntryURL(reportDir, testDesc) {
-    def classDir = urlEncode(testDesc.getClassName())
-    def testDir = urlEncode(sanitizedTestName(testDesc))
-    return "file://${reportDir}/${classDir}/${testDir}"
-}
-
-def getTestResultEntryOutputFile(reportDir, testDesc, fileName) {
-    def dir = getTestReportEntryDir(reportDir, testDesc).toPath()
-    return dir.resolve(fileName).toFile()
-}
-
-def withTestResultEntryWriter(reportDir, testDesc, fileName, append, fn) {
-    def file = getTestResultEntryOutputFile(reportDir, testDesc, fileName)
-    new FileWriter(file, append).withCloseable fn
-}
-
-static def getGitBranchName() {
-    def out = new StringBuilder()
-    def err = new StringBuilder()
-    def proc = "git rev-parse --abbrev-ref HEAD".execute()
-    proc.waitForProcessOutput(out, err)
-    return out.toString().trim()
-}
-
-static def getFreshTestReportIndex(File reportDir) {
-    def number = 0
-    while (true) {
-        def freshIndex = reportDir.toPath().resolve("index.${number++}.html").toFile()
-        if (!freshIndex.exists()) {
-            return freshIndex
-        }
-    }
-}
-
-def forEachTestReportAlreadyX(File reportDir, fileName, onTest) {
-    def out = new StringBuilder()
-    def err = new StringBuilder()
-    def proc = "find . -name ${fileName}".execute([], reportDir)
-    proc.waitForProcessOutput(out, err)
-    def outString = out.toString()
-    outString.eachLine {
-        // Lines are of the form: ./<class>/<name>/FAILURE
-        def clazz = null
-        def name = null
-        try {
-            def trimmed = it.trim()
-            def line = trimmed.substring(2)
-            def sep = line.indexOf("/")
-            clazz = line.substring(0, sep)
-            name = line.substring(sep + 1, line.length() - fileName.length() - 1)
-        } catch (Exception e) {
-            logger.lifecycle("WARNING: failed attempt to read test description from: '${it}'")
-            return
-        }
-        onTest(clazz, desanitizedTestName(name))
-    }
-    return !outString.trim().isEmpty()
-}
-
-def forEachTestReportAlreadyFailing(File reportDir, onFailureTest) {
-    return forEachTestReportAlreadyX(reportDir, TestResult.ResultType.FAILURE.name(), onFailureTest)
-}
-
-def forEachTestReportAlreadyPassing(File reportDir, onSucceededTest) {
-    return forEachTestReportAlreadyX(reportDir, TestResult.ResultType.SUCCESS.name(), onSucceededTest)
-}
-
-def forEachTestReportAlreadySkipped(File reportDir, onSucceededTest) {
-    return forEachTestReportAlreadyX(reportDir, TestResult.ResultType.SKIPPED.name(), onSucceededTest)
-}
-
-def setUpTestingState(Test task) {
-    // Hide all test events from the console, they are written to the report.
-    task.testLogging { events = [] }
-
-    def branch = project.hasProperty('testing-state-name')
-        ? project.getProperty('testing-state-name')
-        : getGitBranchName()
-    def reportDir = file("${buildDir}/test-state/${branch}")
-    def index = reportDir.toPath().resolve("index.html").toFile()
-    def resetState = project.hasProperty('reset-testing-state')
-    def reportDirExists = reportDir.exists()
-    def resuming = !resetState && reportDirExists
-
-    def hasFailingTests = false;
-    if (resuming) {
-        // Test filtering happens before the test execution is initiated so compute it here.
-        // If there are still failing tests in the report, include only those.
-        hasFailingTests = forEachTestReportAlreadyFailing(reportDir, {
-            clazz, name -> task.filter.includeTestsMatching("$clazz.$name")
-        })
-        // Otherwise exclude all of the test already marked as succeeding.
-        if (!hasFailingTests) {
-            // Also allow the test to overall succeed if there are no remaining tests that match,
-            // which is natural if the state already succeeded in full.
-            task.filter.failOnNoMatchingTests = false
-            forEachTestReportAlreadyPassing(reportDir, {
-                clazz, name -> task.filter.excludeTestsMatching("$clazz.$name")
-            })
-            forEachTestReportAlreadySkipped(reportDir, {
-                clazz, name -> task.filter.excludeTestsMatching("$clazz.$name")
-            })
-        }
-    }
-
-    task.beforeSuite { desc ->
-        if (!desc.parent) {
-            def parentReport = null
-            if (resetState && reportDirExists) {
-                delete reportDir
-            }
-            if (resuming) {
-                if (index.exists()) {
-                    parentReport = getFreshTestReportIndex(reportDir)
-                    index.renameTo(parentReport)
-                }
-            } else {
-                reportDir.mkdirs()
-            }
-            def runPrefix = resuming ? "Resuming" : "Starting"
-            def title =  "${runPrefix} @ ${branch}"
-            // Print a console link to the test report for easy access.
-            println "${runPrefix} test, report written to:"
-            println "  file://${index}"
-            // Print the new index content.
-            index << "<html><head><title>${title}</title>"
-            index << "<style> * { font-family: monospace; }</style>"
-            index << "<meta http-equiv='refresh' content='10' />"
-            index << "</head><body><h1>${title}</h1>"
-            index << "<p>Run on: ${new Date()}</p>"
-            index << "<p>Git branch: ${branch}</p>"
-            if (parentReport != null) {
-                index << "<p><a href=\"file://${parentReport}\">Previous result index</a></p>"
-            }
-            index << "<p><a href=\"file://${index}\">Most recent result index</a></p>"
-            index << "<p><a href=\"file://${reportDir}\">Test directories</a></p>"
-            index << "<h2>Failing tests (refreshing automatically every 10 seconds)</h2><ul>"
-        }
-    }
-
-    task.afterSuite { desc, result ->
-        if (!desc.parent) {
-            // Update the final test results in the index.
-            index << "</ul>"
-            if (result.resultType == TestResult.ResultType.SUCCESS) {
-                if (hasFailingTests) {
-                    index << "<h2>Rerun of failed tests now pass!</h2>"
-                    index << "<h2>Rerun again to continue with outstanding tests!</h2>"
-                } else {
-                    index << "<h2 style=\"background-color:#62D856\">GREEN BAR == YOU ROCK!</h2>"
-                }
-            } else if (result.resultType == TestResult.ResultType.FAILURE) {
-                index << "<h2 style=\"background-color:#6D130A\">Some tests failed: ${result.resultType.name()}</h2><ul>"
-            } else {
-                index << "<h2>Tests finished: ${result.resultType.name()}</h2><ul>"
-            }
-            index << "<li>Number of tests: ${result.testCount}"
-            index << "<li>Failing tests: ${result.failedTestCount}"
-            index << "<li>Successful tests: ${result.successfulTestCount}"
-            index << "<li>Skipped tests: ${result.skippedTestCount}"
-            index << "</ul></body></html>"
-        }
-    }
-
-    // Events to stdout/err are appended to the files in the test directories.
-    task.onOutput { desc, event ->
-        withTestResultEntryWriter(reportDir, desc, event.getDestination().name(), true, {
-            it.append(event.getMessage())
-        })
-    }
-
-    task.beforeTest { desc ->
-        // Remove any stale output files before running the test.
-        for (def destType : TestOutputEvent.Destination.values()) {
-            def destFile = getTestResultEntryOutputFile(reportDir, desc, destType.name())
-            if (destFile.exists()) {
-                delete destFile
-            }
-        }
-    }
-
-    task.afterTest { desc, result ->
-        if (result.getTestCount() != 1) {
-            throw new IllegalStateException("Unexpected test with more than one result: ${desc}")
-        }
-        // Clear any previous result files.
-        for (def resultType : TestResult.ResultType.values()) {
-            delete getTestResultEntryOutputFile(reportDir, desc, resultType.name())
-        }
-        // Emit the result type status in a file of the same name: SUCCESS, FAILURE or SKIPPED.
-        withTestResultEntryWriter(reportDir, desc, result.getResultType().name(), false, {
-            it.append(result.getResultType().name())
-        })
-        // Emit the test time.
-        withTestResultEntryWriter(reportDir, desc, "time", false, {
-            it.append("${result.getEndTime() - result.getStartTime()}")
-        })
-        // For failed tests, update the index and emit stack trace information.
-        if (result.resultType == TestResult.ResultType.FAILURE) {
-            def title = escapeHtml("${desc.className}.${desc.name}")
-            def link = getTestReportEntryURL(reportDir, desc)
-            index << "<li><a href=\"${link}\">${title}</a></li>"
-            if (!result.exceptions.isEmpty()) {
-                printAllStackTracesToFile(
-                        result.exceptions,
-                        getTestResultEntryOutputFile(
-                                reportDir,
-                                desc,
-                                "exceptions-raw.txt"))
-                filterStackTraces(result)
-                printAllStackTracesToFile(
-                        result.exceptions,
-                        getTestResultEntryOutputFile(
-                                reportDir,
-                                desc,
-                                "exceptions-filtered.txt"))
-                if (shouldRetrace()) {
-                    withTestResultEntryWriter(reportDir, desc, "exceptions-retraced.txt", false, { writer ->
-                        result.exceptions.forEach { writer.append(retrace(it)) }
-                    })
-                }
-            }
-        }
-    }
-}
-
-def testTimes = [:]
-def numberOfTestTimesToPrint = 100
-
-test { task ->
-
-    dependsOn sourceSets.keepanno.output
-    // R8.jar is required for running bootstrap tests.
-    dependsOn r8
-
-    def useTestingState = project.hasProperty('testing-state')
-    if (useTestingState) {
-        setUpTestingState(task)
-    }
-
-    if (project.hasProperty('generate_golden_files_to')) {
-        systemProperty 'generate_golden_files_to', project.property('generate_golden_files_to')
-        assert project.hasProperty('HEAD_sha1')
-        systemProperty 'test_git_HEAD_sha1', project.property('HEAD_sha1')
-    }
-
-    if (project.hasProperty('use_golden_files_in')) {
-        systemProperty 'use_golden_files_in', project.property('use_golden_files_in')
-        assert project.hasProperty('HEAD_sha1')
-        systemProperty 'test_git_HEAD_sha1', project.property('HEAD_sha1')
-    }
-
-    if (project.hasProperty('kotlin_compiler_dev')) {
-        systemProperty 'com.android.tools.r8.kotlincompilerdev', '1';
-    }
-
-    if (project.hasProperty('kotlin_compiler_old')) {
-        systemProperty 'com.android.tools.r8.kotlincompilerold', '1';
-    }
-
-    if (!useTestingState) {
-        testLogging.exceptionFormat = 'full'
-        if (project.hasProperty('print_test_stdout')) {
-            testLogging.showStandardStreams = true
-        }
-    }
-    if (project.hasProperty('dex_vm') && project.property('dex_vm') != 'default') {
-        println "NOTE: Running with non default vm: " + project.property('dex_vm')
-        systemProperty 'dex_vm', project.property('dex_vm')
-    }
-
-    // Forward runtime configurations for test parameters.
-    if (project.hasProperty('runtimes')) {
-        println "NOTE: Running with runtimes: " + project.property('runtimes')
-        systemProperty 'runtimes', project.property('runtimes')
-    }
-
-    if (project.hasProperty('art_profile_rewriting_completeness_check')) {
-        String key = 'com.android.tools.r8.artprofilerewritingcompletenesscheck'
-        String value = project.property('art_profile_rewriting_completeness_check')
-        systemProperty key, value
-    }
-
-    if (project.hasProperty('slow_tests')) {
-        systemProperty 'slow_tests', project.property('slow_tests')
-    }
-
-
-    if (project.hasProperty('desugar_jdk_json_dir')) {
-        systemProperty 'desugar_jdk_json_dir', project.property('desugar_jdk_json_dir')
-    }
-    if (project.hasProperty('desugar_jdk_libs')) {
-        systemProperty 'desugar_jdk_libs', project.property('desugar_jdk_libs')
-    }
-
-    if (!useTestingState) {
-        if (project.hasProperty('print_times') || project.hasProperty('one_line_per_test')) {
-            afterTest { desc, result ->
-                def executionTime = (result.endTime - result.startTime) / 1000
-                testTimes["${desc.name} [${desc.className}]"] = executionTime
-            }
-            afterSuite { desc, result ->
-                // parent is null if all tests are done.
-                if (desc.parent == null) {
-                    def sortedTimes = testTimes.sort({ e1, e2 -> e2.value <=> e1.value })
-                    sortedTimes.eachWithIndex { key, value, i ->
-                        println "$key: $value"
-                    }
-                }
-            }
-        }
-
-        if (project.hasProperty('one_line_per_test')) {
-            beforeTest { desc ->
-                println "Start executing test ${desc.name} [${desc.className}]"
-            }
-
-            afterTest { desc, result ->
-                if (result.resultType == TestResult.ResultType.FAILURE) {
-                    printStackTrace(result)
-                }
-                if (project.hasProperty('update_test_timestamp')) {
-                    file(project.getProperty('update_test_timestamp')).text = new Date().getTime()
-                }
-                println "Done executing test ${desc.name} [${desc.className}] with result: ${result.resultType}"
-            }
-        } else {
-            afterTest { desc, result ->
-                if (result.resultType == TestResult.ResultType.FAILURE) {
-                    printStackTrace(result)
-                }
-            }
-        }
-    }
-    if (project.hasProperty('no_internal')) {
-        exclude "com/android/tools/r8/internal/**"
-    }
-    if (project.hasProperty('only_internal')) {
-        include "com/android/tools/r8/internal/**"
-    }
-
-    if (project.hasProperty('test_namespace')) {
-        include "com/android/tools/r8/" + project.getProperty('test_namespace') + "/**"
-    }
-
-    if (project.hasProperty('tool') && project.property('tool') == 'd8') {
-        // Don't run anything, deprecated
-        println "Running with deprecated tool d8, not running any tests"
-        include ""
-    }
-    if (project.hasProperty('no_arttests')) {
-        exclude "com/android/tools/r8/art/**"
-    }
-    if (project.hasProperty('shard_count') ) {
-      assert project.hasProperty('shard_number')
-      int shard_count = project.getProperty('shard_count') as Integer
-      int shard_number = project.getProperty('shard_number') as Integer
-      assert shard_count < 65536
-      assert shard_number < shard_count
-      exclude {
-        entry ->
-          // Don't leave out directories. Leaving out a directory means all entries below.
-          if (entry.file.isDirectory()) {
-           return false
-          }
-          def first4 = entry.getRelativePath().toString().md5().substring(0, 4)
-          int hash = Integer.parseInt(first4, 16)
-          return hash % shard_count != shard_number
-      }
-    }
-    if (project.hasProperty('test_dir')) {
-        systemProperty 'test_dir', project.property('test_dir')
-    }
-    if (project.hasProperty('command_cache_dir')) {
-        systemProperty 'command_cache_dir', project.property('command_cache_dir')
-    }
-    if (project.hasProperty('command_cache_stats_dir')) {
-        systemProperty 'command_cache_stats_dir', project.property('command_cache_stats_dir')
-    }
-    if (project.hasProperty('r8lib')) {
-        dependsOn configureTestForR8Lib
-        // R8lib should be used instead of the main output and all the tests in
-        // r8 should be mapped and exists in r8LibTestPath.
-        classpath = sourceSets.test.runtimeClasspath.filter {
-            !it.getAbsolutePath().contains("/build/")
-        }
-        classpath += files([r8LibPath, r8LibTestPath])
-        testClassesDirs = files(r8LibTestPath)
-    }
-    if (OperatingSystem.current().isLinux()
-            || OperatingSystem.current().isMacOsX()
-            || OperatingSystem.current().isWindows()) {
-        if (OperatingSystem.current().isMacOsX()) {
-            logger.lifecycle("WARNING: Testing in only partially supported on Mac OS. " +
-                "Art only runs on Linux and tests requiring Art runs in a Docker container, which must be present. " +
-                "See tools/docker/README.md for details.")
-        }
-        if (OperatingSystem.current().isWindows()) {
-            logger.lifecycle("WARNING: Testing in only partially supported on Windows. " +
-                    "Art only runs on Linux and tests requiring Art will be skipped")
-        }
-        dependsOn downloadDeps
-        dependsOn buildExamples
-    } else {
-        logger.lifecycle("WARNING: Testing in not supported on your platform. Testing is only fully supported on " +
-            "Linux and partially supported on Mac OS and Windows. Art does not run on other platforms.")
-    }
-}
-
-
-task javadocD8(type: Javadoc) {
-  title "D8 API"
-  classpath = sourceSets.main.compileClasspath
-  source = sourceSets.main.allJava
-  include '**/com/android/tools/r8/ArchiveClassFileProvider.java'
-  include '**/com/android/tools/r8/ArchiveProgramResourceProvider.java'
-  include '**/com/android/tools/r8/BaseCommand.java'
-  include '**/com/android/tools/r8/BaseCompilerCommand.java'
-  include '**/com/android/tools/r8/ClassFileResourceProvider.java'
-  include '**/com/android/tools/r8/CompilationFailedException.java'
-  include '**/com/android/tools/r8/CompilationMode.java'
-  include '**/com/android/tools/r8/D8.java'
-  include '**/com/android/tools/r8/D8Command.java'
-  include '**/com/android/tools/r8/DexIndexedConsumer.java'
-  include '**/com/android/tools/r8/DexFilePerClassFileConsumer.java'
-  include '**/com/android/tools/r8/Diagnostic.java'
-  include '**/com/android/tools/r8/DiagnosticsHandler.java'
-  include '**/com/android/tools/r8/DirectoryClassFileProvider.java'
-  include '**/com/android/tools/r8/OutputMode.java'
-  include '**/com/android/tools/r8/ProgramConsumer.java'
-  include '**/com/android/tools/r8/ProgramResource.java'
-  include '**/com/android/tools/r8/ProgramResourceProvider.java'
-  include '**/com/android/tools/r8/Resource.java'
-  include '**/com/android/tools/r8/ResourceException.java'
-  include '**/com/android/tools/r8/StringConsumer.java'
-  include '**/com/android/tools/r8/StringResource.java'
-  include '**/com/android/tools/r8/Version.java'
-  include '**/com/android/tools/r8/origin/*.java'
-}
-
-task javadocR8(type: Javadoc) {
-  title "R8 API"
-  classpath = sourceSets.main.compileClasspath
-  source = sourceSets.main.allJava
-  include '**/com/android/tools/r8/ArchiveClassFileProvider.java'
-  include '**/com/android/tools/r8/ArchiveProgramResourceProvider.java'
-  include '**/com/android/tools/r8/BaseCommand.java'
-  include '**/com/android/tools/r8/BaseCompilerCommand.java'
-  include '**/com/android/tools/r8/ClassFileConsumer.java'
-  include '**/com/android/tools/r8/ClassFileResourceProvider.java'
-  include '**/com/android/tools/r8/CompilationFailedException.java'
-  include '**/com/android/tools/r8/CompilationMode.java'
-  include '**/com/android/tools/r8/R8.java'
-  include '**/com/android/tools/r8/R8Command.java'
-  include '**/com/android/tools/r8/DexIndexedConsumer.java'
-  include '**/com/android/tools/r8/Diagnostic.java'
-  include '**/com/android/tools/r8/DiagnosticsHandler.java'
-  include '**/com/android/tools/r8/DirectoryClassFileProvider.java'
-  include '**/com/android/tools/r8/OutputMode.java'
-  include '**/com/android/tools/r8/ProgramConsumer.java'
-  include '**/com/android/tools/r8/ProgramResource.java'
-  include '**/com/android/tools/r8/ProgramResourceProvider.java'
-  include '**/com/android/tools/r8/Resource.java'
-  include '**/com/android/tools/r8/ResourceException.java'
-  include '**/com/android/tools/r8/StringConsumer.java'
-  include '**/com/android/tools/r8/StringResource.java'
-  include '**/com/android/tools/r8/Version.java'
-  include '**/com/android/tools/r8/origin/*.java'
-}
-
-task copyMavenDeps(type: Copy) {
-    from configurations.compile into "$buildDir/deps"
-    from configurations.compileClasspath into "$buildDir/deps"
-    from configurations.testCompile into "$buildDir/deps"
-}
-
-task printMavenDeps {
-    // Only actually print to stdout when we are updating.
-    if (project.hasProperty('updatemavendeps')) {
-        for (Configuration config : configurations) {
-            if (!config.isCanBeResolved()) {
-                continue
-            }
-            def componentIds = config.incoming.resolutionResult.allDependencies.collect {
-                it.selected.id
-            }
-            def result = dependencies.createArtifactResolutionQuery()
-                .forComponents(componentIds)
-                .withArtifacts(MavenModule, MavenPomArtifact)
-                .execute()
-            for (component in result.resolvedComponents) {
-                component.getArtifacts(MavenPomArtifact).each {
-                    println "POM: ${it.file} ${component.id}"
-                }
-            }
-            config.each {
-                println "JAR: ${it}"
-            }
-        }
-    }
-}
-
-allprojects {
-  tasks.withType(Exec) {
-    doFirst {
-      println commandLine.join(' ')
-    }
-  }
-}
diff --git a/settings.gradle b/settings.gradle
deleted file mode 100644
index 969cb9c..0000000
--- a/settings.gradle
+++ /dev/null
@@ -1,25 +0,0 @@
-// Copyright (c) 2019, 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 org.gradle.internal.os.OperatingSystem
-
-rootProject.name = 'r8'
-
-// Bootstrap building by downloading dependencies.
-def dependencies_bucket = "r8-deps"
-def dependencies_sha1_file = "third_party/dependencies.tar.gz.sha1"
-def extension = OperatingSystem.current().isWindows() ? ".bat" : ".py"
-
-def cmd =
-        ("download_from_google_storage${extension} --extract"
-                + " --bucket ${dependencies_bucket}"
-                + " --sha1_file ${dependencies_sha1_file}")
-def process = cmd.execute()
-process.waitFor()
-if (process.exitValue() != 0) {
-    throw new GradleException(
-            "Bootstrapping dependencies download failed:\n"
-                    + "STDOUT:\n${process.in.text}\n"
-                    + "STDERR:\n${process.err.text}")
-}
\ No newline at end of file
