blob: aa81cdcf2976993d96a55de4237ce79aa0421f87 [file] [log] [blame]
/*
* Copyright (C) 2015 The Android Open Source Project
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package com.android.jack.test.junit;
import com.android.jack.test.toolchain.AbstractTestTools;
import com.android.jack.test.toolchain.IToolchain;
import com.android.sched.util.collect.Lists;
import org.junit.experimental.categories.Categories;
import org.junit.runner.Description;
import org.junit.runner.manipulation.Filter;
import org.junit.runner.manipulation.NoTestsRemainException;
import org.junit.runners.model.InitializationError;
import org.junit.runners.model.RunnerBuilder;
import javax.annotation.Nonnull;
/**
* This runner handles {@link KnownIssue} annotation.
* It filters out tests if current toolchains match those listed in the annotation.
*/
public class JackTestRunner extends Categories {
private boolean dumpTests = false;
@Nonnull
private RuntimeVersion runtimeVersion;
private static class ToolchainFilter extends Filter {
@Nonnull
private IToolchain candidate;
@Nonnull
private IToolchain reference;
private boolean dumpTests = false;
@Nonnull
private RuntimeVersion runtimeVersion;
public ToolchainFilter(@Nonnull IToolchain candidate, @Nonnull IToolchain reference,
boolean dumpTest, @Nonnull RuntimeVersion runtimeVersion) {
this.candidate = candidate;
this.reference = reference;
this.dumpTests = dumpTest;
this.runtimeVersion = runtimeVersion;
}
@Override
@Nonnull
public String describe() {
return "Filters excluded toolchains";
}
@Override
public boolean shouldRun(@Nonnull Description description) {
boolean shouldRun = false;
KnownIssue knownIssueAnnot = description.getAnnotation(KnownIssue.class);
Runtime runtimeAnnot = description.getAnnotation(Runtime.class);
// Special case of ecj tests that use JUnit3
boolean ecjTestEligibleToRun = false;
boolean isEcjTestPostM = false;
if (description.getClassName().contains("Ecj")) {
isEcjTestPostM =
(description.getClassName().contains("PostM"))
|| description.getClassName().contains("EcjInterfaceMethodsTest");
shouldRun =
// Otherwise method of class aren't scanned and dump won't work
(dumpTests && description.getMethodName() == null)
|| (isEcjTestPostM && runtimeVersion.compareTo(RuntimeVersion.N) >= 0);
} else {
// General case
if (runtimeAnnot == null
|| runtimeAnnot.from().compareTo(runtimeVersion) <= 0) {
if (knownIssueAnnot == null) {
shouldRun = true;
} else {
shouldRun =
(knownIssueAnnot.candidate().length > 0 || knownIssueAnnot.reference().length > 0)
&& (isValidToolchain(candidate, knownIssueAnnot.candidate())
&& isValidToolchain(reference, knownIssueAnnot.reference()));
}
}
}
if (dumpTests && description.getMethodName() != null) {
System.out.println(
" \"" + description.getClassName() + '#' + description.getMethodName() + "\": {");
System.out.print(" \"ignored\":" + !shouldRun);
if (runtimeAnnot != null) {
System.out.println(",");
System.out.println(
" \"runtimePostM\":"
+ (runtimeAnnot.from().ordinal() > RuntimeVersion.M.ordinal()));
} else if (description.getClassName().contains("Ecj")) {
// Special case for Ecj tests that use JUnit3
System.out.println(",");
System.out.println(" \"runtimePostM\":" + isEcjTestPostM);
} else {
System.out.println();
}
System.out.println(" },");
return false;
}
return shouldRun;
}
private boolean isValidToolchain(
@Nonnull IToolchain currentToolchain,
@Nonnull Class<? extends IToolchain>[] excludedToolchains) {
for (Class<? extends IToolchain> c : Lists.create(excludedToolchains)) {
if (c.isAssignableFrom(currentToolchain.getClass())) {
return false;
}
}
return true;
}
}
public JackTestRunner(@Nonnull Class<?> klass, @Nonnull RunnerBuilder builder)
throws InitializationError {
super(klass, builder);
dumpTests = Boolean.parseBoolean(System.getProperty("tests.dump", "false"));
runtimeVersion =
RuntimeVersion.valueOf(System.getProperty("runtime.version", "M").toUpperCase());
ToolchainFilter filter = new ToolchainFilter(AbstractTestTools.getCandidateToolchain(),
AbstractTestTools.getReferenceToolchain(), dumpTests, runtimeVersion);
try {
filter(filter);
} catch (NoTestsRemainException e) {
if (!dumpTests) {
throw new InitializationError(e);
}
}
}
}