diff options
author | Fabian Mastenbroek <fabianishere@outlook.com> | 2018-07-11 21:36:11 +0200 |
---|---|---|
committer | Evgeny Mandrikov <Godin@users.noreply.github.com> | 2018-07-11 21:36:11 +0200 |
commit | ce7de98c76b8bd107c05a061193de76d21c4c205 (patch) | |
tree | 5fa095296ab31165b1ac99c2eb1dfc85ea62ff50 /org.jacoco.core/src/org/jacoco/core/internal/analysis | |
parent | c8b8c9d3b7605fc09517c78f385fe31dccf04e31 (diff) | |
download | jacoco-ce7de98c76b8bd107c05a061193de76d21c4c205.tar.gz |
Filter branch generated by kotlinc for reading lateinit properties (#707)
Diffstat (limited to 'org.jacoco.core/src/org/jacoco/core/internal/analysis')
3 files changed, 70 insertions, 1 deletions
diff --git a/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/AbstractMatcher.java b/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/AbstractMatcher.java index fcd1c888..d4b421ef 100644 --- a/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/AbstractMatcher.java +++ b/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/AbstractMatcher.java @@ -67,6 +67,18 @@ abstract class AbstractMatcher { cursor = null; } + final void nextIsInvokeStatic(final String owner, final String name) { + nextIs(Opcodes.INVOKESTATIC); + if (cursor == null) { + return; + } + final MethodInsnNode m = (MethodInsnNode) cursor; + if (owner.equals(m.owner) && name.equals(m.name)) { + return; + } + cursor = null; + } + final void nextIsVar(final int opcode, final String name) { nextIs(opcode); if (cursor == null) { diff --git a/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/Filters.java b/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/Filters.java index cafb1f77..b235e1e6 100644 --- a/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/Filters.java +++ b/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/Filters.java @@ -32,7 +32,7 @@ public final class Filters implements IFilter { new FinallyFilter(), new PrivateEmptyNoArgConstructorFilter(), new StringSwitchJavacFilter(), new LombokGeneratedFilter(), new GroovyGeneratedFilter(), new EnumEmptyConstructorFilter(), - new KotlinGeneratedFilter()); + new KotlinGeneratedFilter(), new KotlinLateinitFilter()); private final IFilter[] filters; diff --git a/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/KotlinLateinitFilter.java b/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/KotlinLateinitFilter.java new file mode 100644 index 00000000..c1aee3ad --- /dev/null +++ b/org.jacoco.core/src/org/jacoco/core/internal/analysis/filter/KotlinLateinitFilter.java @@ -0,0 +1,57 @@ +/******************************************************************************* + * Copyright (c) 2009, 2018 Mountainminds GmbH & Co. KG and Contributors + * All rights reserved. This program and the accompanying materials + * are made available under the terms of the Eclipse Public License v1.0 + * which accompanies this distribution, and is available at + * http://www.eclipse.org/legal/epl-v10.html + * + * Contributors: + * Fabian Mastenbroek - initial API and implementation + * + *******************************************************************************/ +package org.jacoco.core.internal.analysis.filter; + +import org.objectweb.asm.Opcodes; +import org.objectweb.asm.tree.AbstractInsnNode; +import org.objectweb.asm.tree.MethodNode; + +/** + * Filters branch in bytecode that Kotlin compiler generates for reading from + * <code>lateinit</code> properties. + */ +public class KotlinLateinitFilter implements IFilter { + + private final static String OWNER = "kotlin/jvm/internal/Intrinsics"; + private final static String NAME = "throwUninitializedPropertyAccessException"; + + public void filter(final MethodNode methodNode, final IFilterContext context, + final IFilterOutput output) { + for (AbstractInsnNode i = methodNode.instructions + .getFirst(); i != null; i = i.getNext()) { + if (i.getOpcode() != Opcodes.IFNONNULL) { + continue; + } + + final AbstractInsnNode end = new Matcher(i).match(); + + if (end != null) { + output.ignore(i, end); + } + } + } + + private static class Matcher extends AbstractMatcher { + private final AbstractInsnNode start; + + private Matcher(final AbstractInsnNode start) { + this.start = start; + } + + private AbstractInsnNode match() { + cursor = start; + nextIs(Opcodes.LDC); + nextIsInvokeStatic(OWNER, NAME); + return cursor; + } + } +} |