Extend ART/D8 testing with a subsequent R8/debug step, also:

add CompilationMode support for TestConditions

Bug:
Change-Id: Ic8af625d6df971914a2f5d8452889d53b9ab1469
diff --git a/src/test/java/com/android/tools/r8/JctfTestSpecifications.java b/src/test/java/com/android/tools/r8/JctfTestSpecifications.java
index 49c0837..03eddc7 100644
--- a/src/test/java/com/android/tools/r8/JctfTestSpecifications.java
+++ b/src/test/java/com/android/tools/r8/JctfTestSpecifications.java
@@ -5,8 +5,8 @@
 package com.android.tools.r8;
 
 import static com.android.tools.r8.TestCondition.D8_COMPILER;
-import static com.android.tools.r8.TestCondition.R8_COMPILER;
 import static com.android.tools.r8.TestCondition.R8DEBUG_AFTER_D8_COMPILER;
+import static com.android.tools.r8.TestCondition.R8_COMPILER;
 import static com.android.tools.r8.TestCondition.any;
 import static com.android.tools.r8.TestCondition.match;
 import static com.android.tools.r8.TestCondition.runtimes;
@@ -4808,32 +4808,37 @@
           .put("lang.RuntimePermission.Class.RuntimePermission_class_A13", any())
           .build(); // end of timeoutsWithArt
 
-  private static final boolean testMatch(Multimap<String, TestCondition> testConditions,
+  private static final boolean testMatch(
+      Multimap<String, TestCondition> testConditions,
       String name,
-      CompilerUnderTest compilerUnderTest, DexVm dexVm) {
+      CompilerUnderTest compilerUnderTest,
+      DexVm dexVm,
+      CompilationMode compilationMode) {
     Collection<TestCondition> entries = testConditions.get(name);
     for (TestCondition entry : entries) {
-      if (entry.test(DexTool.NONE, compilerUnderTest, dexVm)) {
+      if (entry.test(DexTool.NONE, compilerUnderTest, dexVm, compilationMode)) {
         return true;
       }
     }
     return false;
   }
 
-  public static final Outcome getExpectedOutcome(String name,
+  public static final Outcome getExpectedOutcome(
+      String name,
       CompilerUnderTest compilerUnderTest,
-      DexVm dexVm) {
+      DexVm dexVm,
+      CompilationMode compilationMode) {
 
     Outcome outcome = null;
 
-    if (testMatch(failuresToTriage, name, compilerUnderTest, dexVm)) {
+    if (testMatch(failuresToTriage, name, compilerUnderTest, dexVm, compilationMode)) {
       outcome = Outcome.FAILS_WITH_ART;
     }
-    if (testMatch(timeoutsWithArt, name, compilerUnderTest, dexVm)) {
+    if (testMatch(timeoutsWithArt, name, compilerUnderTest, dexVm, compilationMode)) {
       assert outcome == null;
       outcome = Outcome.TIMEOUTS_WITH_ART;
     }
-    if (testMatch(flakyWithArt, name, compilerUnderTest, dexVm)) {
+    if (testMatch(flakyWithArt, name, compilerUnderTest, dexVm, compilationMode)) {
       assert outcome == null;
       outcome = Outcome.FLAKY_WITH_ART;
     }
diff --git a/src/test/java/com/android/tools/r8/R8RunArtTestsTest.java b/src/test/java/com/android/tools/r8/R8RunArtTestsTest.java
index 5c5975c..8f1dadd 100644
--- a/src/test/java/com/android/tools/r8/R8RunArtTestsTest.java
+++ b/src/test/java/com/android/tools/r8/R8RunArtTestsTest.java
@@ -459,7 +459,9 @@
           // large array as still live and the subsequent allocations will fail to reach the desired
           // size before an out-of-memory error occurs. See:
           // tests/art/{dx,jack}/104-growth-limit/src/Main.java:40
-          .put("104-growth-limit", TestCondition.match(TestCondition.R8_COMPILER))
+          .put(
+              "104-growth-limit",
+              TestCondition.match(TestCondition.R8_COMPILER, TestCondition.RELEASE_MODE))
           .put(
               "461-get-reference-vreg",
               TestCondition.match(
@@ -790,28 +792,23 @@
     }
   }
 
-  private static Map<SpecificationKey, TestSpecification> AVAILABLE_TESTS_MAP_R8 =
-      data(CompilerUnderTest.R8);
-
-  private static Map<SpecificationKey, TestSpecification> AVAILABLE_TESTS_MAP_D8 =
-      data(CompilerUnderTest.D8);
-
-
-  private static Set<String> collectTestsMatchingConditions(DexTool dexTool,
-      CompilerUnderTest compilerUnderTest, DexVm dexVm,
+  private static Set<String> collectTestsMatchingConditions(
+      DexTool dexTool,
+      CompilerUnderTest compilerUnderTest,
+      DexVm dexVm,
+      CompilationMode mode,
       Multimap<String, TestCondition> testConditionsMap) {
     Set<String> set = Sets.newHashSet();
     for (Map.Entry<String, TestCondition> kv : testConditionsMap.entries()) {
-      if (kv.getValue().test(dexTool, compilerUnderTest, dexVm)) {
+      if (kv.getValue().test(dexTool, compilerUnderTest, dexVm, mode)) {
         set.add(kv.getKey());
       }
     }
     return set;
   }
 
-
-  private static Map<SpecificationKey, TestSpecification> data(
-      CompilerUnderTest compilerUnderTest) {
+  private static Map<SpecificationKey, TestSpecification> get_tests_map(
+      CompilerUnderTest compilerUnderTest, CompilationMode compilationMode) {
     File artTestDir = new File(ART_TESTS_DIR);
     if (!artTestDir.exists()) {
       // Don't run any tests if the directory does not exist.
@@ -834,8 +831,9 @@
     DexVm dexVm = ToolHelper.getDexVm();
     for (DexTool dexTool : DexTool.values()) {
       // Collect the tests failing code generation.
-      Set<String> failsWithCompiler = collectTestsMatchingConditions(dexTool, compilerUnderTest,
-          dexVm, failingWithCompiler);
+      Set<String> failsWithCompiler =
+          collectTestsMatchingConditions(
+              dexTool, compilerUnderTest, dexVm, compilationMode, failingWithCompiler);
 
       // Collect tests that has no input:
       if (dexTool == DexTool.NONE) {
@@ -843,15 +841,18 @@
       }
 
       // Collect the test that we should skip in this configuration.
-      skipArt.addAll(collectTestsMatchingConditions(dexTool, compilerUnderTest,
-          dexVm, timeoutOrSkipRunWithArt));
+      skipArt.addAll(
+          collectTestsMatchingConditions(
+              dexTool, compilerUnderTest, dexVm, compilationMode, timeoutOrSkipRunWithArt));
 
       // Collect the tests failing to run in Art (we still run R8/D8 on these).
-      Set<String> failsWithArt = collectTestsMatchingConditions(dexTool, compilerUnderTest, dexVm,
-          failingRunWithArt);
+      Set<String> failsWithArt =
+          collectTestsMatchingConditions(
+              dexTool, compilerUnderTest, dexVm, compilationMode, failingRunWithArt);
       {
-        Set<String> tmpSet = collectTestsMatchingConditions(dexTool, compilerUnderTest, dexVm,
-            expectedToFailRunWithArt);
+        Set<String> tmpSet =
+            collectTestsMatchingConditions(
+                dexTool, compilerUnderTest, dexVm, compilationMode, expectedToFailRunWithArt);
         failsWithArt.addAll(tmpSet);
       }
 
@@ -863,14 +864,17 @@
       }
 
       // Collect the tests failing with output differences in Art.
-      Set<String> failsRunWithArtOutput = collectTestsMatchingConditions(dexTool, compilerUnderTest,
-          dexVm, failingRunWithArtOutput);
-      Set<String> expectedToFailWithCompilerSet = collectTestsMatchingConditions(dexTool,
-          compilerUnderTest, dexVm, expectedToFailWithCompiler);
+      Set<String> failsRunWithArtOutput =
+          collectTestsMatchingConditions(
+              dexTool, compilerUnderTest, dexVm, compilationMode, failingRunWithArtOutput);
+      Set<String> expectedToFailWithCompilerSet =
+          collectTestsMatchingConditions(
+              dexTool, compilerUnderTest, dexVm, compilationMode, expectedToFailWithCompiler);
 
       // Collect the tests where the original works in Art and the R8/D8 generated output does not.
-      Set<String> failsRunWithArtOriginalOnly = collectTestsMatchingConditions(dexTool,
-          compilerUnderTest, dexVm, failingRunWithArtOriginalOnly);
+      Set<String> failsRunWithArtOriginalOnly =
+          collectTestsMatchingConditions(
+              dexTool, compilerUnderTest, dexVm, compilationMode, failingRunWithArtOriginalOnly);
 
       File compilerTestDir = artTestDir.toPath().resolve(dexToolDirectory(dexTool)).toFile();
       File[] testDirs = compilerTestDir.listFiles();
@@ -895,6 +899,22 @@
     return data;
   }
 
+  private static CompilationMode defaultCompilationMode(CompilerUnderTest compilerUnderTest) {
+    CompilationMode compilationMode = null;
+    switch (compilerUnderTest) {
+      case R8:
+        compilationMode = CompilationMode.RELEASE;
+        break;
+      case D8:
+      case R8DEBUG_AFTER_D8:
+        compilationMode = CompilationMode.DEBUG;
+        break;
+      default:
+        throw new RuntimeException("Unreachable.");
+    }
+    return compilationMode;
+  }
+
   private static String dexToolDirectory(DexTool tool) {
     // DexTool.NONE uses class files in the dx directory.
     return tool == DexTool.JACK ? "jack" : "dx";
@@ -936,12 +956,6 @@
   }
 
   private void executeCompilerUnderTest(
-      CompilerUnderTest compilerUnderTest, Collection<String> fileNames, String resultPath)
-      throws IOException, ProguardRuleParserException, ExecutionException, CompilationException {
-    executeCompilerUnderTest(compilerUnderTest, fileNames, resultPath, null, null);
-  }
-
-  private void executeCompilerUnderTest(
       CompilerUnderTest compilerUnderTest,
       Collection<String> fileNames,
       String resultPath,
@@ -957,43 +971,48 @@
       CompilationMode mode,
       String keepRulesFile)
       throws IOException, ProguardRuleParserException, ExecutionException, CompilationException {
+    assert mode != null;
     switch (compilerUnderTest) {
-      case D8: {
-        assert keepRulesFile == null : "Keep-rules file specified for D8.";
-        D8Command.Builder builder =
-            D8Command.builder()
-                .setMode(mode == null ? CompilationMode.DEBUG : mode)
-                .addProgramFiles(ListUtils.map(fileNames, Paths::get));
-        Integer minSdkVersion = needMinSdkVersion.get(name);
-        if (minSdkVersion != null) {
-          builder.setMinApiLevel(minSdkVersion);
-        }
-        D8Output output = D8.run(builder.build());
-        output.write(Paths.get(resultPath));
-        break;
-      }
-      case R8: {
-        R8Command.Builder builder =
-            R8Command.builder()
-                .setMode(mode == null ? CompilationMode.RELEASE : mode)
-                .setOutputPath(Paths.get(resultPath))
-                .addProgramFiles(ListUtils.map(fileNames, Paths::get))
-                .setIgnoreMissingClasses(true);
-        Integer minSdkVersion = needMinSdkVersion.get(name);
-        if (minSdkVersion != null) {
-          builder.setMinApiLevel(minSdkVersion);
-        }
-        if (keepRulesFile != null) {
-          builder.addProguardConfigurationFiles(Paths.get(keepRulesFile));
-        }
-        // Add internal flags for testing purposes.
-        ToolHelper.runR8(builder.build(), options -> {
-          if (enableInterfaceMethodDesugaring.contains(name)) {
-            options.interfaceMethodDesugaring = OffOrAuto.Auto;
+      case D8:
+        {
+          assert keepRulesFile == null : "Keep-rules file specified for D8.";
+          D8Command.Builder builder =
+              D8Command.builder()
+                  .setMode(mode)
+                  .addProgramFiles(ListUtils.map(fileNames, Paths::get));
+          Integer minSdkVersion = needMinSdkVersion.get(name);
+          if (minSdkVersion != null) {
+            builder.setMinApiLevel(minSdkVersion);
           }
-        });
-        break;
-      }
+          D8Output output = D8.run(builder.build());
+          output.write(Paths.get(resultPath));
+          break;
+        }
+      case R8:
+        {
+          R8Command.Builder builder =
+              R8Command.builder()
+                  .setMode(mode)
+                  .setOutputPath(Paths.get(resultPath))
+                  .addProgramFiles(ListUtils.map(fileNames, Paths::get))
+                  .setIgnoreMissingClasses(true);
+          Integer minSdkVersion = needMinSdkVersion.get(name);
+          if (minSdkVersion != null) {
+            builder.setMinApiLevel(minSdkVersion);
+          }
+          if (keepRulesFile != null) {
+            builder.addProguardConfigurationFiles(Paths.get(keepRulesFile));
+          }
+          // Add internal flags for testing purposes.
+          ToolHelper.runR8(
+              builder.build(),
+              options -> {
+                if (enableInterfaceMethodDesugaring.contains(name)) {
+                  options.interfaceMethodDesugaring = OffOrAuto.Auto;
+                }
+              });
+          break;
+        }
       default:
         assert false : compilerUnderTest;
     }
@@ -1003,7 +1022,7 @@
     return builder.setMinification(false);
   }
 
-  private static final boolean isAuxClassFile(String fileName, String auxClassFileBase) {
+  private static boolean isAuxClassFile(String fileName, String auxClassFileBase) {
     return fileName.endsWith(".class")
         && (fileName.startsWith(auxClassFileBase + "$")
         || fileName.startsWith(auxClassFileBase + "_"));
@@ -1060,11 +1079,13 @@
         compilerUnderTest == CompilerUnderTest.R8DEBUG_AFTER_D8
             ? CompilerUnderTest.D8
             : compilerUnderTest;
+    CompilationMode compilationMode = defaultCompilationMode(compilerUnderTest);
 
     File resultDir = temp.newFolder(firstCompilerUnderTest.toString().toLowerCase() + "-output");
 
-    JctfTestSpecifications.Outcome expectedOutcome = JctfTestSpecifications
-        .getExpectedOutcome(name, firstCompilerUnderTest, dexVm);
+    JctfTestSpecifications.Outcome expectedOutcome =
+        JctfTestSpecifications.getExpectedOutcome(
+            name, firstCompilerUnderTest, dexVm, compilationMode);
     TestSpecification specification = new TestSpecification(name, DexTool.NONE, resultDir,
         expectedOutcome == JctfTestSpecifications.Outcome.TIMEOUTS_WITH_ART
             || expectedOutcome == JctfTestSpecifications.Outcome.FLAKY_WITH_ART,
@@ -1133,11 +1154,12 @@
       fileNames.add(f.getCanonicalPath());
     }
 
-    runJctfTestDoRunOnArt(fileNames,
+    runJctfTestDoRunOnArt(
+        fileNames,
         specification,
         firstCompilerUnderTest,
         fullClassName,
-        null,
+        compilationMode,
         dexVm,
         resultDir);
 
@@ -1149,8 +1171,10 @@
               .map(Path::toString)
               .collect(Collectors.toList());
       File r8ResultDir = temp.newFolder("r8-output");
-      expectedOutcome = JctfTestSpecifications
-          .getExpectedOutcome(name, CompilerUnderTest.R8DEBUG_AFTER_D8, dexVm);
+      compilationMode = CompilationMode.DEBUG;
+      expectedOutcome =
+          JctfTestSpecifications.getExpectedOutcome(
+              name, CompilerUnderTest.R8DEBUG_AFTER_D8, dexVm, compilationMode);
       specification = new TestSpecification(name, DexTool.DX, r8ResultDir,
           expectedOutcome == JctfTestSpecifications.Outcome.TIMEOUTS_WITH_ART
               || expectedOutcome == JctfTestSpecifications.Outcome.FLAKY_WITH_ART,
@@ -1163,7 +1187,7 @@
           specification,
           CompilerUnderTest.R8,
           fullClassName,
-          CompilationMode.DEBUG,
+          compilationMode,
           dexVm,
           r8ResultDir);
     }
@@ -1234,16 +1258,16 @@
 
   protected void runArtTest(DexVm version, CompilerUnderTest compilerUnderTest)
       throws Throwable {
-    Map<SpecificationKey, TestSpecification> specificationMap = null;
+    CompilerUnderTest firstCompilerUnderTest =
+        compilerUnderTest == CompilerUnderTest.R8DEBUG_AFTER_D8
+            ? CompilerUnderTest.D8
+            : compilerUnderTest;
 
-    if (compilerUnderTest == CompilerUnderTest.R8) {
-      specificationMap = AVAILABLE_TESTS_MAP_R8;
-    } else {
-      assert (compilerUnderTest == CompilerUnderTest.D8);
-      specificationMap = AVAILABLE_TESTS_MAP_D8;
-    }
+    CompilationMode compilationMode = defaultCompilationMode(compilerUnderTest);
 
-    TestSpecification specification = specificationMap.get(new SpecificationKey(name, toolchain));
+    TestSpecification specification =
+        get_tests_map(firstCompilerUnderTest, compilationMode)
+            .get(new SpecificationKey(name, toolchain));
 
     if (specification == null) {
       throw new RuntimeException("Test " + name + " has no specification for toolchain"
@@ -1280,12 +1304,52 @@
     for (File file : inputFiles) {
       fileNames.add(file.getCanonicalPath());
     }
-    File resultDir = temp.getRoot();
 
+    File resultDir = temp.newFolder(firstCompilerUnderTest.toString().toLowerCase() + "-output");
+
+    runArtTestDoRunOnArt(
+        version, firstCompilerUnderTest, specification, fileNames, resultDir, compilationMode);
+
+    if (compilerUnderTest == CompilerUnderTest.R8DEBUG_AFTER_D8) {
+      compilationMode = CompilationMode.DEBUG;
+      specification =
+          get_tests_map(CompilerUnderTest.R8DEBUG_AFTER_D8, compilationMode)
+              .get(new SpecificationKey(name, DexTool.DX));
+
+      if (specification == null) {
+        throw new RuntimeException(
+            "Test " + name + " has no specification for toolchain" + toolchain + ".");
+      }
+
+      if (specification.skipTest) {
+        return;
+      }
+
+      fileNames.clear();
+      for (File file : resultDir.listFiles((File file) -> file.getName().endsWith(".dex"))) {
+        fileNames.add(file.getCanonicalPath());
+      }
+
+      resultDir = temp.newFolder("r8-output");
+
+      runArtTestDoRunOnArt(
+          version, CompilerUnderTest.R8, specification, fileNames, resultDir, compilationMode);
+    }
+  }
+
+  private void runArtTestDoRunOnArt(
+      DexVm version,
+      CompilerUnderTest compilerUnderTest,
+      TestSpecification specification,
+      List<String> fileNames,
+      File resultDir,
+      CompilationMode compilationMode)
+      throws Throwable {
     if (specification.expectedToFailWithX8) {
       thrown.expect(CompilationError.class);
       try {
-        executeCompilerUnderTest(compilerUnderTest, fileNames, resultDir.getCanonicalPath());
+        executeCompilerUnderTest(
+            compilerUnderTest, fileNames, resultDir.getCanonicalPath(), compilationMode, null);
       } catch (CompilationException e) {
         throw new CompilationError(e.getMessage(), e);
       } catch (ExecutionException e) {
@@ -1295,11 +1359,13 @@
       return;
     } else if (specification.failsWithX8) {
       thrown.expect(Throwable.class);
-      executeCompilerUnderTest(compilerUnderTest, fileNames, resultDir.getCanonicalPath());
+      executeCompilerUnderTest(
+          compilerUnderTest, fileNames, resultDir.getCanonicalPath(), compilationMode);
       System.err.println("Should have failed R8/D8 compilation with an exception.");
       return;
     } else {
-      executeCompilerUnderTest(compilerUnderTest, fileNames, resultDir.getCanonicalPath());
+      executeCompilerUnderTest(
+          compilerUnderTest, fileNames, resultDir.getCanonicalPath(), compilationMode);
     }
 
     if (!specification.skipArt && ToolHelper.artSupported()) {
diff --git a/src/test/java/com/android/tools/r8/TestCondition.java b/src/test/java/com/android/tools/r8/TestCondition.java
index 5ffd779..eabc95e 100644
--- a/src/test/java/com/android/tools/r8/TestCondition.java
+++ b/src/test/java/com/android/tools/r8/TestCondition.java
@@ -38,27 +38,46 @@
     }
   }
 
+  static class CompilationModeSet {
+
+    final EnumSet<CompilationMode> set;
+
+    public CompilationModeSet(EnumSet<CompilationMode> set) {
+      this.set = set;
+    }
+  }
+
   public static final CompilerSet D8_COMPILER = compilers(CompilerUnderTest.D8);
   public static final CompilerSet R8_COMPILER = compilers(CompilerUnderTest.R8);
   public static final CompilerSet R8DEBUG_AFTER_D8_COMPILER =
       compilers(CompilerUnderTest.R8DEBUG_AFTER_D8);
 
+  public static final CompilationModeSet DEBUG_MODE =
+      new CompilationModeSet(EnumSet.of(CompilationMode.DEBUG));
+  public static final CompilationModeSet RELEASE_MODE =
+      new CompilationModeSet(EnumSet.of(CompilationMode.RELEASE));
+
   private static final ToolSet ANY_TOOL = new ToolSet(EnumSet.allOf(DexTool.class));
   private static final CompilerSet ANY_COMPILER =
       new CompilerSet(EnumSet.allOf(CompilerUnderTest.class));
   private static final RuntimeSet ANY_RUNTIME = new RuntimeSet(EnumSet.allOf(DexVm.class));
+  private static final CompilationModeSet ANY_MODE =
+      new CompilationModeSet(EnumSet.allOf(CompilationMode.class));
 
   private final EnumSet<DexTool> dexTools;
   private final EnumSet<CompilerUnderTest> compilers;
   private final EnumSet<DexVm> dexVms;
+  private final EnumSet<CompilationMode> compilationModes;
 
   public TestCondition(
       EnumSet<DexTool> dexTools,
       EnumSet<CompilerUnderTest> compilers,
-      EnumSet<DexVm> dexVms) {
+      EnumSet<DexVm> dexVms,
+      EnumSet<CompilationMode> compilationModes) {
     this.dexTools = dexTools;
     this.compilers = compilers;
     this.dexVms = dexVms;
+    this.compilationModes = compilationModes;
   }
 
   public static ToolSet tools(DexTool... tools) {
@@ -76,8 +95,16 @@
     return new RuntimeSet(EnumSet.copyOf(Arrays.asList(runtimes)));
   }
 
+  public static TestCondition match(
+      ToolSet tools,
+      CompilerSet compilers,
+      RuntimeSet runtimes,
+      CompilationModeSet compilationModes) {
+    return new TestCondition(tools.set, compilers.set, runtimes.set, compilationModes.set);
+  }
+
   public static TestCondition match(ToolSet tools, CompilerSet compilers, RuntimeSet runtimes) {
-    return new TestCondition(tools.set, compilers.set, runtimes.set);
+    return match(tools, compilers, runtimes, TestCondition.ANY_MODE);
   }
 
   public static TestCondition any() {
@@ -100,6 +127,10 @@
     return match(TestCondition.ANY_TOOL, compilers, TestCondition.ANY_RUNTIME);
   }
 
+  public static TestCondition match(CompilerSet compilers, CompilationModeSet compilationModes) {
+    return match(TestCondition.ANY_TOOL, compilers, TestCondition.ANY_RUNTIME, compilationModes);
+  }
+
   public static TestCondition match(CompilerSet compilers, RuntimeSet runtimes) {
     return match(TestCondition.ANY_TOOL, compilers, runtimes);
   }
@@ -108,7 +139,11 @@
     return match(TestCondition.ANY_TOOL, TestCondition.ANY_COMPILER, runtimes);
   }
 
-  public boolean test(DexTool dexTool, CompilerUnderTest compilerUnderTest, DexVm dexVm) {
+  public boolean test(
+      DexTool dexTool,
+      CompilerUnderTest compilerUnderTest,
+      DexVm dexVm,
+      CompilationMode compilationMode) {
     // R8DEBUG_AFTER_D8 will be set in the R8 phase of the D8-then-R8 tests. So R8DEBUG_AFTER_D8
     // must match both with plain R8 and itself.
     boolean compilerMatches = compilers.contains(compilerUnderTest)
@@ -116,6 +151,7 @@
             && compilers.contains(CompilerUnderTest.R8));
     return dexTools.contains(dexTool)
         && compilerMatches
-        && dexVms.contains(dexVm);
+        && dexVms.contains(dexVm)
+        && compilationModes.contains(compilationMode);
   }
 }
diff --git a/tools/create_art_tests.py b/tools/create_art_tests.py
index 3a83cbc..69d2be7 100755
--- a/tools/create_art_tests.py
+++ b/tools/create_art_tests.py
@@ -63,9 +63,13 @@
   for dir in dirs:
     class_name = "Art" + dir.replace("-", "_") + "Test"
     for tool in TOOLS:
+      if tool == "d8" and toolchain == "none":
+        tool_enum = 'R8DEBUG_AFTER_D8'
+      else:
+        tool_enum = upper(tool)
       contents = TEMPLATE.substitute(
           name=dir,
-          compilerUnderTestEnum=upper(tool),
+          compilerUnderTestEnum=tool_enum,
           compilerUnderTest=tool,
           testGeneratingToolchain=toolchain,
           testGeneratingToolchainEnum=upper(toolchain),