ClassAnalyzer.java

    1/*******************************************************************************
    2 * Copyright (c) 2009 Mountainminds GmbH & Co. KG and others
    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 *    Marc R. Hoffmann - initial API and implementation
   10 *    
   11 * $Id: $
   12 *******************************************************************************/
   13package org.jacoco.core.instr;
   14
   15import org.jacoco.core.data.IClassStructureVisitor;
   16import org.jacoco.core.data.IMethodStructureVisitor;
   17import org.objectweb.asm.AnnotationVisitor;
   18import org.objectweb.asm.Attribute;
   19import org.objectweb.asm.ClassVisitor;
   20import org.objectweb.asm.FieldVisitor;
   21import org.objectweb.asm.MethodVisitor;
   22import org.objectweb.asm.Opcodes;
   23
   24/**
   25 * A {@link ClassVisitor} that analyzes the executable blocks of a class.
   26 * 
   27 * @author Marc R. Hoffmann
   28 * @version $Revision: $
   29 */
   30public class ClassAnalyzer implements ClassVisitor {
   31
   32    private final IClassStructureVisitor structureVisitor;
   33
   34    private int methodCount;
   35
   36    /**
   37     * Creates a new analyzer that reports to the given
   38     * {@link IClassStructureVisitor} instance.
   39     * 
   40     * @param structureVisitor
   41     *            consumer for class structure output
   42     */
   43    public ClassAnalyzer(final IClassStructureVisitor structureVisitor) {
   44        this.structureVisitor = structureVisitor;
   45        methodCount = 0;
   46    }
   47
   48    public void visit(final int version, final int access, final String name,
   49            final String signature, final String superName,
   50            final String[] interfaces) {
   51    }
   52
   53    public void visitSource(final String source, final String debug) {
   54        if (source != null) {
   55            structureVisitor.visitSourceFile(source);
   56        }
   57    }
   58
   59    public AnnotationVisitor visitAnnotation(final String desc,
   60            final boolean visible) {
   61        return null;
   62    }
   63
   64    public void visitInnerClass(final String name, final String outerName,
   65            final String innerName, final int access) {
   66    }
   67
   68    public void visitOuterClass(final String owner, final String name,
   69            final String desc) {
   70    }
   71
   72    public void visitAttribute(final Attribute attr) {
   73    }
   74
   75    public FieldVisitor visitField(final int access, final String name,
   76            final String desc, final String signature, final Object value) {
   77        return null;
   78    }
   79
   80    public MethodVisitor visitMethod(final int access, final String name,
   81            final String desc, final String signature, final String[] exceptions) {
   82
   83        // Abstract methods do not have code to analyze
   84        if ((access & Opcodes.ACC_ABSTRACT) != 0) {
   85            return null;
   86        }
   87
   88        // TODO: Use filter hook
   89        if ((access & Opcodes.ACC_SYNTHETIC) != 0) {
   90            return null;
   91        }
   92
   93        final IMethodStructureVisitor structure = structureVisitor
   94                .visitMethodStructure(methodCount++, name, desc, signature);
   95        return new BlockMethodAdapter(new MethodAnalyzer(structure), access,
   96                name, desc, signature, exceptions);
   97    }
   98
   99    public void visitEnd() {
  100        structureVisitor.visitEnd();
  101    }
  102
  103}