Home | History | Annotate | Download | only in filter
      1 /*******************************************************************************
      2  * Copyright (c) 2009, 2018 Mountainminds GmbH & Co. KG and Contributors
      3  * All rights reserved. This program and the accompanying materials
      4  * are made available under the terms of the Eclipse Public License v1.0
      5  * which accompanies this distribution, and is available at
      6  * http://www.eclipse.org/legal/epl-v10.html
      7  *
      8  * Contributors:
      9  *    Evgeny Mandrikov - initial API and implementation
     10  *
     11  *******************************************************************************/
     12 package org.jacoco.core.internal.analysis.filter;
     13 
     14 import static org.junit.Assert.assertEquals;
     15 import static org.junit.Assert.assertNull;
     16 import static org.junit.Assert.fail;
     17 
     18 import org.jacoco.core.internal.instr.InstrSupport;
     19 import org.junit.Test;
     20 import org.objectweb.asm.Label;
     21 import org.objectweb.asm.Opcodes;
     22 import org.objectweb.asm.tree.AbstractInsnNode;
     23 import org.objectweb.asm.tree.LabelNode;
     24 import org.objectweb.asm.tree.MethodNode;
     25 
     26 public class SynchronizedFilterTest implements IFilterOutput {
     27 
     28 	private final SynchronizedFilter filter = new SynchronizedFilter();
     29 
     30 	private final MethodNode m = new MethodNode(InstrSupport.ASM_API_VERSION, 0,
     31 			"name", "()V", null, null);
     32 
     33 	private AbstractInsnNode fromInclusive;
     34 	private AbstractInsnNode toInclusive;
     35 
     36 	@Test
     37 	public void javac() {
     38 		final Label start = new Label();
     39 		final Label end = new Label();
     40 		final Label handler = new Label();
     41 		final Label handlerEnd = new Label();
     42 		m.visitTryCatchBlock(start, end, handler, null);
     43 		m.visitTryCatchBlock(handler, handlerEnd, handler, null);
     44 
     45 		m.visitVarInsn(Opcodes.ALOAD, 0);
     46 		m.visitFieldInsn(Opcodes.GETFIELD, "Fun", "lock", "Ljava/lang/Object;");
     47 		m.visitInsn(Opcodes.DUP);
     48 		m.visitVarInsn(Opcodes.ASTORE, 1);
     49 		m.visitInsn(Opcodes.MONITORENTER);
     50 		m.visitLabel(start);
     51 		m.visitInsn(Opcodes.NOP);
     52 		m.visitVarInsn(Opcodes.ALOAD, 1);
     53 		m.visitInsn(Opcodes.MONITOREXIT);
     54 		m.visitLabel(end);
     55 		final Label exit = new Label();
     56 		m.visitJumpInsn(Opcodes.GOTO, exit);
     57 		m.visitLabel(handler);
     58 		m.visitVarInsn(Opcodes.ASTORE, 2);
     59 		m.visitVarInsn(Opcodes.ALOAD, 1);
     60 		m.visitInsn(Opcodes.MONITOREXIT);
     61 		m.visitLabel(handlerEnd);
     62 		m.visitVarInsn(Opcodes.ALOAD, 2);
     63 		m.visitInsn(Opcodes.ATHROW);
     64 		m.visitLabel(exit);
     65 		m.visitInsn(Opcodes.RETURN);
     66 
     67 		filter.filter("Foo", "java/lang/Object", m, this);
     68 		assertEquals(handler.info, fromInclusive);
     69 		assertEquals(((LabelNode) exit.info).getPrevious(), toInclusive);
     70 	}
     71 
     72 	/**
     73 	 * <pre>
     74 	 *     try {
     75 	 *         ...
     76 	 *     } catch (Exception e) {
     77 	 *         ...
     78 	 *     } finally {
     79 	 *         ...
     80 	 *     }
     81 	 * </pre>
     82 	 */
     83 	@Test
     84 	public void javacTryCatchFinally() {
     85 		final Label start = new Label();
     86 		final Label end = new Label();
     87 		final Label catchHandler = new Label();
     88 		final Label finallyHandler = new Label();
     89 		final Label catchHandlerEnd = new Label();
     90 		m.visitTryCatchBlock(start, end, catchHandler, "java/lang/Exception");
     91 		m.visitTryCatchBlock(start, end, finallyHandler, null);
     92 		m.visitTryCatchBlock(catchHandler, catchHandlerEnd, finallyHandler,
     93 				null);
     94 
     95 		m.visitLabel(start);
     96 		// body
     97 		m.visitInsn(Opcodes.NOP);
     98 		m.visitLabel(end);
     99 		// finally
    100 		m.visitInsn(Opcodes.NOP);
    101 		final Label exit = new Label();
    102 		m.visitJumpInsn(Opcodes.GOTO, exit);
    103 		m.visitLabel(catchHandler);
    104 		m.visitVarInsn(Opcodes.ASTORE, 1);
    105 		// catch
    106 		m.visitInsn(Opcodes.NOP);
    107 		m.visitLabel(catchHandlerEnd);
    108 		// finally
    109 		m.visitInsn(Opcodes.NOP);
    110 		m.visitJumpInsn(Opcodes.GOTO, exit);
    111 		m.visitLabel(finallyHandler);
    112 		m.visitVarInsn(Opcodes.ASTORE, 2);
    113 		// finally
    114 		m.visitInsn(Opcodes.NOP);
    115 		m.visitVarInsn(Opcodes.ALOAD, 2);
    116 		m.visitInsn(Opcodes.ATHROW);
    117 		m.visitLabel(exit);
    118 		m.visitInsn(Opcodes.RETURN);
    119 
    120 		filter.filter("Foo", "java/lang/Object", m, this);
    121 		assertNull(fromInclusive);
    122 	}
    123 
    124 	@Test
    125 	public void ecj() {
    126 		final Label start = new Label();
    127 		final Label end = new Label();
    128 		final Label handler = new Label();
    129 		final Label handlerEnd = new Label();
    130 		m.visitTryCatchBlock(start, end, handler, null);
    131 		m.visitTryCatchBlock(handler, handlerEnd, handler, null);
    132 
    133 		m.visitVarInsn(Opcodes.ALOAD, 0);
    134 		m.visitFieldInsn(Opcodes.GETFIELD, "Target", "lock",
    135 				"Ljava/lang/Object;");
    136 		m.visitInsn(Opcodes.DUP);
    137 		m.visitVarInsn(Opcodes.ASTORE, 1);
    138 		m.visitInsn(Opcodes.MONITORENTER);
    139 		m.visitLabel(start);
    140 		m.visitVarInsn(Opcodes.ALOAD, 0);
    141 		m.visitInsn(Opcodes.NOP);
    142 		m.visitVarInsn(Opcodes.ALOAD, 1);
    143 		m.visitInsn(Opcodes.MONITOREXIT);
    144 		m.visitLabel(end);
    145 		final Label exit = new Label();
    146 		m.visitJumpInsn(Opcodes.GOTO, exit);
    147 		m.visitLabel(handler);
    148 		m.visitVarInsn(Opcodes.ALOAD, 1);
    149 		m.visitInsn(Opcodes.MONITOREXIT);
    150 		m.visitLabel(handlerEnd);
    151 		m.visitInsn(Opcodes.ATHROW);
    152 		m.visitLabel(exit);
    153 		m.visitInsn(Opcodes.RETURN);
    154 
    155 		filter.filter("Foo", "java/lang/Object", m, this);
    156 		assertEquals(handler.info, fromInclusive);
    157 		assertEquals(((LabelNode) exit.info).getPrevious(), toInclusive);
    158 	}
    159 
    160 	public void ignore(AbstractInsnNode fromInclusive,
    161 			AbstractInsnNode toInclusive) {
    162 		assertNull(this.fromInclusive);
    163 		this.fromInclusive = fromInclusive;
    164 		this.toInclusive = toInclusive;
    165 	}
    166 
    167 	public void merge(final AbstractInsnNode i1, final AbstractInsnNode i2) {
    168 		fail();
    169 	}
    170 
    171 }
    172