Update desugared library tests to not use any source set building

Bug: b/270105162
Bug: b/289346278
Change-Id: Ifc207a6355328bf4bf00242e215dec280ed4a420
diff --git a/build.gradle b/build.gradle
index 834e3d6..04704bc 100644
--- a/build.gradle
+++ b/build.gradle
@@ -139,11 +139,6 @@
             srcDirs = ['src/test/examplesJava20']
         }
     }
-    examplesTestNGRunner {
-        java {
-            srcDirs = ['src/test/testngrunner']
-        }
-    }
     examplesAndroidN {
         java {
             srcDirs = ['src/test/examplesAndroidN']
@@ -245,8 +240,6 @@
     main17Implementation group: 'org.ow2.asm', name: 'asm-analysis', version: asmVersion
     main17Implementation group: 'org.ow2.asm', name: 'asm-util', version: asmVersion
 
-    examplesTestNGRunnerCompile group: 'org.testng', name: 'testng', version: testngVersion
-
     testCompile sourceSets.examples.output
     testCompile "junit:junit:$junitVersion"
     testCompile "com.google.guava:guava:$guavaVersion"
@@ -624,11 +617,6 @@
         JavaVersion.VERSION_11,
         false)
 setJdkCompilationWithCompatibility(
-        sourceSets.examplesTestNGRunner.compileJavaTaskName,
-        'jdk-11',
-        JavaVersion.VERSION_11,
-        false)
-setJdkCompilationWithCompatibility(
         sourceSets.examplesJava17.compileJavaTaskName,
         'jdk-17',
         JavaVersion.VERSION_17,
@@ -640,19 +628,6 @@
         JavaVersion.VERSION_17,
         false)
 
-task provideJdk11TestsDependencies(type: org.gradle.api.tasks.Copy) {
-    from sourceSets.examplesTestNGRunner.compileClasspath
-    include "**/**.jar"
-    into file("$buildDir/test/jdk11Tests")
-}
-
-task compileTestNGRunner (type: JavaCompile) {
-    dependsOn provideJdk11TestsDependencies
-    destinationDir = file("$buildDir/classes/java/examplesTestNGRunner")
-    source = sourceSets.examplesTestNGRunner.allSource
-    classpath = sourceSets.examplesTestNGRunner.compileClasspath
-}
-
 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) {
@@ -2232,7 +2207,6 @@
         dependsOn buildExamples
         dependsOn buildKotlinR8TestResources
         dependsOn buildPreNJdwpTestsJar
-        dependsOn compileTestNGRunner
         dependsOn provideArtFrameworksDependencies
     } else {
         logger.lifecycle("WARNING: Testing in not supported on your platform. Testing is only fully supported on " +
diff --git a/src/test/java/com/android/tools/r8/ToolHelper.java b/src/test/java/com/android/tools/r8/ToolHelper.java
index 447399f..8ffd594 100644
--- a/src/test/java/com/android/tools/r8/ToolHelper.java
+++ b/src/test/java/com/android/tools/r8/ToolHelper.java
@@ -118,6 +118,7 @@
   public static final String GENERATED_TEST_BUILD_DIR = BUILD_DIR + "generated/test/";
   public static final String LIBS_DIR = BUILD_DIR + "libs/";
   public static final String THIRD_PARTY_DIR = getProjectRoot() + "third_party/";
+  public static final String DEPENDENCIES = THIRD_PARTY_DIR + "dependencies/";
   public static final String TOOLS_DIR = getProjectRoot() + "tools/";
   public static final String TESTS_DIR = getProjectRoot() + "src/test/";
   public static final String TESTS_SOURCE_DIR = TESTS_DIR + "java/";
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11AtomicTests.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11AtomicTests.java
index ddeddc0..3ac00b5 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11AtomicTests.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11AtomicTests.java
@@ -4,8 +4,9 @@
 
 package com.android.tools.r8.desugar.desugaredlibrary.jdktests;
 
-import static com.android.tools.r8.ToolHelper.JDK_TESTS_BUILD_DIR;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getPathsFiles;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getTestNGMainRunner;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGPath;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGSupportProgramFiles;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.CompilationSpecification.D8_L8DEBUG;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.CompilationSpecification.D8_L8SHRINK;
@@ -27,7 +28,6 @@
 import com.google.common.collect.ImmutableList;
 import java.nio.file.Path;
 import java.nio.file.Paths;
-import java.util.Collections;
 import java.util.List;
 import org.junit.BeforeClass;
 import org.junit.Test;
@@ -79,8 +79,7 @@
   public static void compileAtomicClasses() throws Exception {
     ATOMIC_COMPILED_TESTS_FOLDER = getStaticTemp().newFolder("atomic").toPath();
     javac(TestRuntime.getCheckedInJdk11(), getStaticTemp())
-        .addClasspathFiles(
-            Collections.singletonList(Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar")))
+        .addClasspathFiles(testNGPath())
         .addSourceFiles(ATOMIC_TESTS_FILES)
         .setOutputPath(ATOMIC_COMPILED_TESTS_FOLDER)
         .compile();
@@ -93,6 +92,7 @@
         .addProgramFiles(
             ATOMIC_COMPILED_TESTS_FOLDER.resolve(ATOMIC_REFERENCE_TEST + CLASS_EXTENSION))
         .addProgramFiles(testNGSupportProgramFiles())
+        .addProgramClassFileData(getTestNGMainRunner())
         .applyIf(
             !libraryDesugaringSpecification.hasNioFileDesugaring(parameters),
             b -> b.addProgramFiles(getPathsFiles()))
@@ -110,6 +110,7 @@
         .addProgramFiles(
             getAllFilesWithSuffixInDirectory(ATOMIC_COMPILED_TESTS_FOLDER, CLASS_EXTENSION))
         .addProgramFiles(testNGSupportProgramFiles())
+        .addProgramClassFileData(getTestNGMainRunner())
         .applyIf(
             !libraryDesugaringSpecification.hasNioFileDesugaring(parameters),
             b -> b.addProgramFiles(getPathsFiles()))
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11ConcurrentLinkedQueueTests.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11ConcurrentLinkedQueueTests.java
index d8bc956..87478e0 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11ConcurrentLinkedQueueTests.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11ConcurrentLinkedQueueTests.java
@@ -4,7 +4,8 @@
 
 package com.android.tools.r8.desugar.desugaredlibrary.jdktests;
 
-import static com.android.tools.r8.ToolHelper.JDK_TESTS_BUILD_DIR;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getTestNGMainRunner;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGPath;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGSupportProgramFiles;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.CompilationSpecification.D8_L8DEBUG;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.CompilationSpecification.D8_L8SHRINK;
@@ -40,7 +41,6 @@
 import com.google.common.collect.ImmutableSet;
 import java.nio.file.Path;
 import java.nio.file.Paths;
-import java.util.Collections;
 import java.util.List;
 import org.junit.BeforeClass;
 import org.junit.Ignore;
@@ -92,8 +92,7 @@
     Path jdk11ConcurrentLinkedQueueTestsDir =
         getStaticTemp().newFolder("ConcurrentLinkedQueue").toPath();
     javac(TestRuntime.getCheckedInJdk11(), getStaticTemp())
-        .addClasspathFiles(
-            Collections.singletonList(Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar")))
+        .addClasspathFiles(testNGPath())
         .addSourceFiles(JDK_11_CONCURRENT_LINKED_QUEUE_JAVA_FILES)
         .setOutputPath(jdk11ConcurrentLinkedQueueTestsDir)
         .compile();
@@ -182,6 +181,7 @@
                 parameters, libraryDesugaringSpecification, compilationSpecification)
             .addProgramFiles(JDK_11_CONCURRENT_LINKED_QUEUE_TEST_CLASS_FILES)
             .addProgramFiles(testNGSupportProgramFiles())
+            .addProgramClassFileData(getTestNGMainRunner())
             // The WhiteBox test is using VarHandle and MethodHandles.privateLookupIn to inspect the
             // internal state of the implementation, so desugaring is needed for the program here.
             .addOptionsModification(options -> options.enableVarHandleDesugaring = true)
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11ConcurrentMapTests.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11ConcurrentMapTests.java
index f4b8b17..c27bb8b 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11ConcurrentMapTests.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11ConcurrentMapTests.java
@@ -4,8 +4,9 @@
 
 package com.android.tools.r8.desugar.desugaredlibrary.jdktests;
 
-import static com.android.tools.r8.ToolHelper.JDK_TESTS_BUILD_DIR;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getPathsFiles;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getTestNGMainRunner;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGPath;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGSupportProgramFiles;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.CompilationSpecification.D8_L8DEBUG;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.CompilationSpecification.D8_L8SHRINK;
@@ -82,8 +83,7 @@
   public static void compileConcurrentClasses() throws Exception {
     Path concurrentCompiledTestsFolder = getStaticTemp().newFolder("concurrentmap").toPath();
     javac(TestRuntime.getCheckedInJdk11(), getStaticTemp())
-        .addClasspathFiles(
-            Collections.singletonList(Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar")))
+        .addClasspathFiles(testNGPath())
         .addSourceFiles(getAllFilesWithSuffixInDirectory(CONCURRENT_TESTS_FOLDER, JAVA_EXTENSION))
         .setOutputPath(concurrentCompiledTestsFolder)
         .compile();
@@ -100,8 +100,7 @@
     Path concurrentHashCompiledTestsFolder =
         getStaticTemp().newFolder("concurrenthashmap").toPath();
     javac(TestRuntime.getCheckedInJdk11(), getStaticTemp())
-        .addClasspathFiles(
-            Collections.singletonList(Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar")))
+        .addClasspathFiles(testNGPath())
         .addSourceFiles(classesToCompile)
         .setOutputPath(concurrentHashCompiledTestsFolder)
         .compile();
@@ -118,6 +117,7 @@
     testForDesugaredLibrary(parameters, libraryDesugaringSpecification, compilationSpecification)
         .addProgramFiles(CONCURRENT_COMPILED_TESTS_FILES)
         .addProgramFiles(testNGSupportProgramFiles())
+        .addProgramClassFileData(getTestNGMainRunner())
         .applyIf(
             !libraryDesugaringSpecification.hasNioFileDesugaring(parameters),
             b -> b.addProgramFiles(getPathsFiles()))
@@ -168,6 +168,7 @@
                 parameters, libraryDesugaringSpecification, compilationSpecification)
             .addProgramFiles(concurrentHashTestToCompile())
             .addProgramFiles(testNGSupportProgramFiles())
+            .addProgramClassFileData(getTestNGMainRunner())
             .applyIf(
                 !libraryDesugaringSpecification.hasNioFileDesugaring(parameters),
                 b -> b.addProgramFiles(getPathsFiles()))
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11NioFileTests.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11NioFileTests.java
index 0f735fe..ed6b91a 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11NioFileTests.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11NioFileTests.java
@@ -4,7 +4,8 @@
 
 package com.android.tools.r8.desugar.desugaredlibrary.jdktests;
 
-import static com.android.tools.r8.ToolHelper.JDK_TESTS_BUILD_DIR;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getTestNGMainRunner;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGPath;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGSupportProgramFiles;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11TestLibraryDesugaringSpecification.EXTENSION_PATH;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11TestLibraryDesugaringSpecification.JDK11_PATH_JAVA_BASE_EXT;
@@ -262,7 +263,7 @@
     Path tmpDirectory = getStaticTemp().newFolder(name).toPath();
     List<Path> classpath = new ArrayList<>();
     classpath.add(EXTENSION_PATH);
-    classpath.add(Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar"));
+    classpath.add(testNGPath());
     if (cp != null) {
       classpath.add(cp);
     }
@@ -284,6 +285,7 @@
             .addProgramFiles(TEST_UTIL_JAR)
             .addProgramClassFileData(TEST_PROGRAM_CLASS_DATA)
             .addProgramFiles(testNGSupportProgramFiles())
+            .addProgramClassFileData(getTestNGMainRunner())
             .compile()
             .withArt6Plus64BitsLib();
     int success = 0;
@@ -341,6 +343,7 @@
             .addProgramFiles(TEST_UTIL_JAR)
             .addProgramClassFileData(TEST_PROGRAM_CLASS_DATA)
             .addProgramFiles(testNGSupportProgramFiles())
+            .addProgramClassFileData(getTestNGMainRunner())
             .addLibraryFiles(libraryDesugaringSpecification.getLibraryFiles())
             .compile()
             .withArt6Plus64BitsLib();
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11StreamAbstractTests.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11StreamAbstractTests.java
index 9ff2346..78b8776 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11StreamAbstractTests.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11StreamAbstractTests.java
@@ -4,9 +4,10 @@
 
 package com.android.tools.r8.desugar.desugaredlibrary.jdktests;
 
-import static com.android.tools.r8.ToolHelper.JDK_TESTS_BUILD_DIR;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getPathsFiles;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getSafeVarArgsFile;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getTestNGMainRunner;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGPath;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGSupportProgramFiles;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11TestLibraryDesugaringSpecification.EXTENSION_PATH;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11TestLibraryDesugaringSpecification.JDK11_PATH_JAVA_BASE_EXT;
@@ -256,8 +257,7 @@
             "java.base=" + EXTENSION_PATH);
     javac(TestRuntime.getCheckedInJdk11(), getStaticTemp())
         .addOptions(options)
-        .addClasspathFiles(
-            ImmutableList.of(EXTENSION_PATH, Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar")))
+        .addClasspathFiles(testNGPath())
         .addSourceFiles(getJdk11StreamTestFiles())
         .setOutputPath(JDK_11_STREAM_TEST_CLASSES_DIR)
         .compile();
@@ -297,6 +297,7 @@
             b -> b.addProgramFiles(getPathsFiles()))
         .addProgramFiles(getSafeVarArgsFile())
         .addProgramFiles(testNGSupportProgramFiles())
+        .addProgramClassFileData(getTestNGMainRunner())
         .addOptionsModification(opt -> opt.testing.trackDesugaredAPIConversions = true)
         .disableL8AnnotationRemoval()
         .compile()
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11SupportFiles.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11SupportFiles.java
index d3507a2..6d99f62 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11SupportFiles.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11SupportFiles.java
@@ -4,7 +4,8 @@
 
 package com.android.tools.r8.desugar.desugaredlibrary.jdktests;
 
-import static com.android.tools.r8.ToolHelper.JDK_TESTS_BUILD_DIR;
+import static com.android.tools.r8.TestBase.descriptor;
+import static com.android.tools.r8.TestBase.transformer;
 
 import com.android.tools.r8.ToolHelper;
 import java.nio.file.Path;
@@ -16,10 +17,11 @@
 
 public class Jdk11SupportFiles {
 
+  // TODO(b/289346278): See if we can remove the xxx subfolder.
   private static final Path ANDROID_PATHS_FILES_DIR =
-      Paths.get("third_party/android_jar/lib-v26/xxx/");
+      Paths.get(ToolHelper.THIRD_PARTY_DIR + "android_jar/lib-v26/xxx/");
   private static final Path ANDROID_SAFE_VAR_ARGS_LOCATION =
-      Paths.get("third_party/android_jar/lib-v26/java/lang/SafeVarargs.class");
+      Paths.get(ToolHelper.THIRD_PARTY_DIR + "android_jar/lib-v26/java/lang/SafeVarargs.class");
   private static final Path[] ANDROID_PATHS_FILES =
       new Path[] {
         Paths.get("java/nio/file/Files.class"),
@@ -40,10 +42,79 @@
   }
 
   public static Path[] testNGSupportProgramFiles() {
-    return new Path[] {
-      Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar"),
-      Paths.get(JDK_TESTS_BUILD_DIR + "jcommander-1.48.jar"),
-      Paths.get(ToolHelper.JAVA_CLASSES_DIR + "examplesTestNGRunner/TestNGMainRunner.class")
-    };
+    return new Path[] {testNGPath(), jcommanderPath()};
+  }
+
+  public static Path testNGPath() {
+    return Paths.get(ToolHelper.DEPENDENCIES + "org/testng/testng/6.10/testng-6.10.jar");
+  }
+
+  public static Path jcommanderPath() {
+    return Paths.get(ToolHelper.DEPENDENCIES + "com/beust/jcommander/1.48/jcommander-1.48.jar");
+  }
+
+  public static byte[] getTestNGMainRunner() throws Exception {
+    return transformer(TestNGMainRunner.class)
+        .setClassDescriptor("LTestNGMainRunner;")
+        .replaceClassDescriptorInMethodInstructions(descriptor(TestNG.class), "Lorg/testng/TestNG;")
+        .replaceClassDescriptorInMethodInstructions(
+            descriptor(TextReporter.class), "Lorg/testng/reporters/TextReporter;")
+        .transform();
+  }
+
+  /** TestNGMainRunner used as the test runner in JDK11 tests. */
+  public static class TestNGMainRunner {
+
+    private static void runTestNg(Class<?> testClass, int verbose) {
+      System.out.println("Running tests in " + testClass.getName());
+      TestNG testng = new TestNG(false);
+      testng.setTestClasses(new Class<?>[] {testClass});
+      testng.setVerbose(verbose);
+      // Deprecated API used because it works on Android unlike the recommended one.
+      testng.addListener(new TextReporter(testClass.getName(), verbose));
+      try {
+        testng.run();
+        System.out.print("Tests result in " + testClass.getName() + ": ");
+        if (testng.hasFailure()) {
+          System.out.println("FAILURE");
+        } else {
+          System.out.println("SUCCESS");
+        }
+      } catch (RuntimeException | Error e) {
+        System.out.print("Tests result in " + testClass.getName() + ": ");
+        System.out.println("ERROR");
+        e.printStackTrace();
+      }
+    }
+
+    public static void main(String[] args) throws Exception {
+      // First arg is the verbosity level.
+      // Second arg is the class to run.
+      int verbose = Integer.parseInt(args[0]);
+      runTestNg(Class.forName(args[1]), verbose);
+    }
+  }
+
+  /** Stubs for the TestNGRunner */
+  public static class TextReporter {
+
+    public TextReporter(String name, int verbose) {}
+  }
+
+  public static class TestNG {
+
+    public TestNG(boolean val) {}
+
+    public void setTestClasses(Class<?>[] classes) {}
+
+    public void setVerbose(int verbose) {}
+
+    public void addListener(Object textReporter) {}
+
+    public void run() {}
+
+    public boolean hasFailure() {
+      return false;
+    }
   }
 }
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11TestLibraryDesugaringSpecification.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11TestLibraryDesugaringSpecification.java
index 7a2760a..f909be9 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11TestLibraryDesugaringSpecification.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11TestLibraryDesugaringSpecification.java
@@ -4,8 +4,8 @@
 
 package com.android.tools.r8.desugar.desugaredlibrary.jdktests;
 
-import static com.android.tools.r8.ToolHelper.JDK_TESTS_BUILD_DIR;
 import static com.android.tools.r8.desugar.desugaredlibrary.DesugaredLibraryTestBase.getAllFilesWithSuffixInDirectory;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGPath;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.LibraryDesugaringSpecification.JDK11;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.LibraryDesugaringSpecification.JDK11_PATH;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.LibraryDesugaringSpecification.JDK8;
@@ -98,8 +98,7 @@
             "java.base=" + JDK_11_JAVA_BASE_EXTENSION_FILES_DIR);
     JavaCompilerTool.create(TestRuntime.getCheckedInJdk11(), folder)
         .addOptions(options)
-        .addClasspathFiles(
-            Collections.singletonList(Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar")))
+        .addClasspathFiles(testNGPath())
         .addSourceFiles(getExtensionsFiles())
         .setOutputPath(output)
         .compile();
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11TimeAbstractTests.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11TimeAbstractTests.java
index a2c95c1..f59341e 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11TimeAbstractTests.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/jdktests/Jdk11TimeAbstractTests.java
@@ -4,8 +4,10 @@
 
 package com.android.tools.r8.desugar.desugaredlibrary.jdktests;
 
-import static com.android.tools.r8.ToolHelper.JDK_TESTS_BUILD_DIR;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getPathsFiles;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.getTestNGMainRunner;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.jcommanderPath;
+import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGPath;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11SupportFiles.testNGSupportProgramFiles;
 import static com.android.tools.r8.desugar.desugaredlibrary.jdktests.Jdk11TestLibraryDesugaringSpecification.EXTENSION_PATH;
 import static com.android.tools.r8.desugar.desugaredlibrary.test.CompilationSpecification.D8_L8DEBUG;
@@ -108,10 +110,7 @@
             "java.base=" + EXTENSION_PATH);
     javac(TestRuntime.getCheckedInJdk11(), getStaticTemp())
         .addOptions(options)
-        .addClasspathFiles(
-            ImmutableList.of(
-                Paths.get(JDK_TESTS_BUILD_DIR + "testng-6.10.jar"),
-                Paths.get(JDK_TESTS_BUILD_DIR + "jcommander-1.48.jar")))
+        .addClasspathFiles(testNGPath(), jcommanderPath())
         .addSourceFiles(getJdk11TimeTestFiles())
         .setOutputPath(tmpDirectory)
         .compile();
@@ -261,6 +260,7 @@
                 parameters, libraryDesugaringSpecification, compilationSpecification)
             .addProgramFiles(JDK_11_TIME_TEST_COMPILED_FILES)
             .addProgramFiles(testNGSupportProgramFiles())
+            .addProgramClassFileData(getTestNGMainRunner())
             .applyIf(
                 !libraryDesugaringSpecification.hasNioFileDesugaring(parameters),
                 b -> b.addProgramFiles(getPathsFiles()))
diff --git a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/test/DesugaredLibraryTestBuilder.java b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/test/DesugaredLibraryTestBuilder.java
index 2cf1e98..c871859 100644
--- a/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/test/DesugaredLibraryTestBuilder.java
+++ b/src/test/java/com/android/tools/r8/desugar/desugaredlibrary/test/DesugaredLibraryTestBuilder.java
@@ -38,6 +38,7 @@
 import java.io.IOException;
 import java.nio.file.Path;
 import java.util.ArrayList;
+import java.util.Arrays;
 import java.util.Collection;
 import java.util.List;
 import java.util.concurrent.ExecutionException;
@@ -182,6 +183,10 @@
     return this;
   }
 
+  public DesugaredLibraryTestBuilder<T> addProgramClassFileData(byte[]... classes) {
+    return addProgramClassFileData(Arrays.asList(classes));
+  }
+
   public DesugaredLibraryTestBuilder<T> addProgramClassFileData(
       Collection<byte[]> programClassFileData) {
     builder.addProgramClassFileData(programClassFileData);
diff --git a/src/test/testngrunner/TestNGMainRunner.java b/src/test/testngrunner/TestNGMainRunner.java
deleted file mode 100644
index 22d96ef..0000000
--- a/src/test/testngrunner/TestNGMainRunner.java
+++ /dev/null
@@ -1,37 +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.
-
-// This class is kept in a separate package because of the org.testng dependency.
-// R8 tests do not depend on testng, this class does.
-public class TestNGMainRunner {
-
-  private static void runTestNg(Class<?> testClass, int verbose) {
-    System.out.println("Running tests in " + testClass.getName());
-    org.testng.TestNG testng = new org.testng.TestNG(false);
-    testng.setTestClasses(new Class<?>[] {testClass});
-    testng.setVerbose(verbose);
-    // Deprecated API used because it works on Android unlike the recommended one.
-    testng.addListener(new org.testng.reporters.TextReporter(testClass.getName(), verbose));
-    try {
-      testng.run();
-      System.out.print("Tests result in " + testClass.getName() + ": ");
-      if (testng.hasFailure()) {
-        System.out.println("FAILURE");
-      } else {
-        System.out.println("SUCCESS");
-      }
-    } catch (RuntimeException | Error e) {
-      System.out.print("Tests result in " + testClass.getName() + ": ");
-      System.out.println("ERROR");
-      e.printStackTrace();
-    }
-  }
-
-  public static void main(String[] args) throws Exception {
-    // First arg is the verbosity level.
-    // Second arg is the class to run.
-    int verbose = Integer.parseInt(args[0]);
-    runTestNg(Class.forName(args[1]), verbose);
-  }
-}