private List<MutationDetails> filter( List<MutationDetails> inEquals, Mutater m) { final Location equalsMethod = inEquals.get(0).getId().getLocation(); final Optional<MethodTree> maybeEquals = this.currentClass.methods().stream() .filter(MethodMatchers.forLocation(equalsMethod)) .findFirst(); return inEquals.stream() .filter(isShortcutEquals(maybeEquals.get(), m).negate()) .collect(Collectors.toList()); }
@Override public boolean test(MutationDetails a) { if (!MUTATOR_ID.equals(a.getMutator())) { return false; } final MethodTree method = NullReturnsFilter.this.currentClass.methods().stream() .filter(MethodMatchers.forLocation(a.getId().getLocation())) .findFirst() .get(); final int mutatedInstruction = a.getInstructionIndex(); return returnsNull(method, mutatedInstruction); }
private Predicate<MutationDetails> isEquivalent(Mutater m) { return a -> { if (!MUTATOR_IDS.contains(a.getMutator())) { return false; } final MethodTree method = PrimitiveEquivalentFilter.this.currentClass.methods().stream() .filter(MethodMatchers.forLocation(a.getId().getLocation())) .findFirst() .get(); return ZERO_CONSTANTS.contains(method.realInstructionBefore(a.getInstructionIndex()).getOpcode()); }; }
private boolean isInfiniteLoop(MutationDetails each, Mutater m) { final ClassTree mutantClass = ClassTree.fromBytes(m.getMutation(each.getId()).getBytes()); final Optional<MethodTree> mutantMethod = mutantClass.methods().stream() .filter(forLocation(each.getId().getLocation())) .findFirst(); return infiniteLoopMatcher().matches(mutantMethod.get().instructions()); }
public void results(final MutationStatusMap allmutations) throws IOException { for (final MutationDetails each : allmutations.allMutations()) { final MutationStatusTestPair status = this.thread.getStatus(each.getId()); if (status != null) { allmutations.setStatusForMutation(each, status); } } }
@Override public void recordResult(final MutationResult result) { final PrintWriter output = this.outputFactory.create(); output.println(serialize(new ObjectOutputStreamHistoryStore.IdResult( result.getDetails().getId(), result.getStatusTestPair()))); output.flush(); }
private static MutationDetails makeCombinedMutant( final Collection<MutationDetails> value) { final MutationDetails first = value.iterator().next(); final Set<Integer> indexes = new HashSet<>(); mapTo(value, mutationToIndex(), indexes); final MutationIdentifier id = new MutationIdentifier(first.getId() .getLocation(), indexes, first.getId().getMutator()); return new MutationDetails(id, first.getFilename(), first.getDescription(), first.getLineNumber(), first.getBlock()); }
private Boolean shortCutEquals(MethodTree tree, MutationDetails a, Mutater m) { if (!mutatesAConditionalJump(tree, a.getInstructionIndex())) { return false; } final ClassTree mutant = ClassTree.fromBytes(m.getMutation(a.getId()).getBytes()); final MethodTree mutantEquals = mutant.methods().stream() .filter(MethodMatchers.forLocation(tree.asLocation())) .findFirst() .get(); return ALWAYS_FALSE.matches(mutantEquals.instructions()); }
protected Mutant getNthMutant(final Collection<MutationDetails> actual, int n) { assertFalse("There are less than " + (n + 1) +" mutants", actual.size() < n + 1 ); Iterator<MutationDetails> i = actual.iterator(); for (int j = 0; j < n && i.hasNext(); j++) { i.next(); } final Mutant mutant = this.engine.getMutation(i.next() .getId()); verifyMutant(mutant); return mutant; }
private Predicate<MutationDetails> mutatesAForLoopCounter() { return a -> { final int instruction = a.getInstructionIndex(); final MethodTree method = AvoidForLoopCounterFilter.this.currentClass.methods().stream() .filter(MethodMatchers.forLocation(a.getId().getLocation())) .findFirst().get(); final AbstractInsnNode mutatedInstruction = method.instruction(instruction); final Context<AbstractInsnNode> context = Context.start(method.instructions(), DEBUG); context.store(MUTATED_INSTRUCTION.write(), mutatedInstruction); return MUTATED_FOR_COUNTER.matches(method.instructions(), context); }; }
protected void assertMutantsAreFrom( final List<MutationDetails> actualDetails, final Class<?>... mutators) { assertEquals(mutators.length, actualDetails.size()); int i = 0; for (final MutationDetails each : actualDetails) { assertEquals(each.getId().getMutator(), mutators[i].getName()); i++; } }
@Test public void shouldDescribeEachExaminedMutation() throws IOException { final MutationDetails mutantOne = makeMutant("foo", 1); final MutationDetails mutantTwo = makeMutant("foo", 2); final Collection<MutationDetails> range = Arrays.asList(mutantOne, mutantTwo); this.testee.run(range, this.reporter, this.testSource); verify(this.reporter).describe(mutantOne.getId()); verify(this.reporter).describe(mutantTwo.getId()); }
@Override public boolean matches(MutationDetails value) { return value.getId().getLocation().getMethodName().name().equals(name); } };
@Test public void shouldScopeMutationIndexesByInstructionCounter() { createTesteeWith(Mutator.byName("RETURN_VALS")); final List<MutationDetails> actualDetails = findMutationsFor(HasTwoMutableMethods.class); assertEquals(2, actualDetails.size()); assertEquals(4, actualDetails.get(0).getId().getFirstIndex()); assertEquals(15, actualDetails.get(1).getId().getFirstIndex()); // differs // by // target? }
@Test public void shouldWriteMutantBytesToDisk() { final Collection<MutationDetails> mutations = executeFor(VeryMutable.class); final Mutant firstMutant = this.mutator.getMutation(mutations.iterator().next().getId()); final Path shouldBeCreated = mutantBasePath(VeryMutable.class,0).resolve(ClassName.fromClass(VeryMutable.class).asJavaName() + ".class"); assertThat(shouldBeCreated).hasBinaryContent(firstMutant.getBytes()); }
@Test @Ignore("disabled while checking coverage issue") public void shouldReportNoCoverageForMutationWithNoTestCoverage() throws IOException { final MutationDetails mutantOne = makeMutant("foo", 1); final Collection<MutationDetails> range = Arrays.asList(mutantOne); this.testee.run(range, this.reporter, this.testSource); verify(this.reporter).report(mutantOne.getId(), MutationStatusTestPair.notAnalysed(0, DetectionStatus.NO_COVERAGE)); }
private void assertOnlyClinitMethodsMarked(Collection<MutationDetails> actual) { for (final MutationDetails each : actual ) { if (each.isInStaticInitializer()) { if (!each.getId().getLocation().getMethodName().name().equals("<clinit>")) { fail("Expected no mutants to be marked as for static initialization but " + each + " was"); } } } }
private Function<MutationDetails, Loc> toLocation(final ClassTree tree) { return a -> { final MethodTree method = tree.method(a.getId().getLocation()).get(); final Loc l = new Loc(); l.index = a.getInstructionIndex(); l.node = method.instruction(a.getInstructionIndex()); return l; }; }
public MutationDetails makeMutant(final String clazz, final int index) { final MutationIdentifier id = aMutationId() .withLocation(aLocation().withClass(ClassName.fromString(clazz))) .withIndex(index).withMutator("mutator").build(); final MutationDetails md = new MutationDetails(id, "sourceFile", "desc", 42, 0); when(this.mutater.getMutation(md.getId())).thenReturn( new Mutant(md, new byte[0])); return md; }
@Test public void shouldGatherStatistics() { final MutationResult mr = makeResult(); this.testee.handleMutationResult(createMetaData(mr)); assertTrue(hasResultFor(mr.getDetails().getId().getMutator())); }