1 package jp.sourceforge.stigmata.birthmarks.wsp;
7 import java.util.ArrayList;
8 import java.util.HashMap;
9 import java.util.Iterator;
10 import java.util.List;
13 import jp.sourceforge.stigmata.Birthmark;
14 import jp.sourceforge.stigmata.BirthmarkElement;
15 import jp.sourceforge.stigmata.BirthmarkEnvironment;
16 import jp.sourceforge.stigmata.ExtractionUnit;
17 import jp.sourceforge.stigmata.birthmarks.ASMBirthmarkExtractor;
18 import jp.sourceforge.stigmata.birthmarks.BirthmarkExtractVisitor;
19 import jp.sourceforge.stigmata.spi.BirthmarkSpi;
21 import org.objectweb.asm.ClassVisitor;
22 import org.objectweb.asm.ClassWriter;
23 import org.objectweb.asm.Label;
24 import org.objectweb.asm.MethodVisitor;
28 * @author Haruaki Tamada
31 public class StackPatternBasedBirthmarkExtractor extends ASMBirthmarkExtractor{
34 public BirthmarkExtractVisitor createExtractVisitor(ClassWriter writer, Birthmark birthmark, BirthmarkEnvironment environment){
35 return new Visitor(writer, birthmark, environment);
38 public StackPatternBasedBirthmarkExtractor(BirthmarkSpi service){
43 public ExtractionUnit[] getAcceptableUnits(){
44 return new ExtractionUnit[] {
45 ExtractionUnit.ARCHIVE, ExtractionUnit.PACKAGE, ExtractionUnit.CLASS,
49 private BirthmarkElement[] buildElement(List<Opcode> opcodes){
50 List<BirthmarkElement> elements = new ArrayList<BirthmarkElement>();
51 Map<Label, Integer> tableMap = new HashMap<Label, Integer>();
54 for(Opcode opcode: opcodes){
55 Integer forwardedStatus = null;
56 if(opcode.getCategory() != Opcode.Category.TARGETER){
57 forwardedStatus = tableMap.get(((LabelOpcode)opcode).getLabel());
59 if(forwardedStatus == null){
60 currentDepth += opcode.getAct();
63 currentDepth = forwardedStatus + opcode.getAct();
65 if(opcode.getCategory() == Opcode.Category.BRANCH){
66 for(Iterator<Label> i = opcode.labels(); i.hasNext(); ){
67 Label label = i.next();
68 tableMap.put(label, currentDepth);
73 return elements.toArray(new BirthmarkElement[elements.size()]);
76 private class Visitor extends BirthmarkExtractVisitor{
77 public Visitor(ClassVisitor visitor, Birthmark birthmark, BirthmarkEnvironment environment){
78 super(visitor, birthmark, environment);
81 public void visitEnd(){
85 public MethodVisitor visitMethod(int arg0, String arg1, String arg2, String arg3, String[] arg4){
86 MethodVisitor visitor = super.visitMethod(arg0, arg1, arg2, arg3, arg4);
87 OpcodeExtractionMethodVisitor opcodeVisitor = new OpcodeExtractionMethodVisitor(visitor);
88 opcodeVisitor.addOpcodeExtractionFinishListener(new OpcodeExtractionFinishListener(){
90 public void finishExtractionOpcodes(List<Opcode> opcodes){
91 BirthmarkElement[] elements = buildElement(opcodes);
93 for(BirthmarkElement be: elements){