1 package org.kit.furia.fragment.asm;
2
3 import java.io.BufferedInputStream;
4 import java.io.File;
5 import java.io.FileInputStream;
6 import java.io.FileNotFoundException;
7 import java.io.FileWriter;
8 import java.io.IOException;
9 import java.util.HashMap;
10 import java.util.HashSet;
11 import java.util.Iterator;
12 import java.util.LinkedList;
13 import java.util.List;
14 import java.util.Map;
15 import java.util.Set;
16
17 import org.apache.log4j.Logger;
18 import org.kit.furia.exceptions.IRException;
19 import org.kit.furia.fragment.AbstractFragmentExtractor;
20 import org.kit.furia.fragment.FragmentParseException;
21 import org.kit.furia.fragment.MTDFragmentAST;
22 import org.kit.furia.fragment.OBFragment;
23 import org.kit.furia.fragment.soot.HugeFragmentException;
24 import org.kit.furia.fragment.soot.NoClassesFound;
25 import org.kit.furia.misc.IntegerHolder;
26 import org.objectweb.asm.ClassReader;
27 import org.objectweb.asm.tree.ClassNode;
28 import org.objectweb.asm.tree.MethodNode;
29 import org.objectweb.asm.tree.analysis.Analyzer;
30 import org.objectweb.asm.tree.analysis.Frame;
31 import org.objectweb.asm.tree.analysis.Value;
32
33 public class FragmentExtractorASM
34 extends AbstractFragmentExtractor {
35
36 private static final Logger logger = Logger.getLogger(FragmentExtractorASM.class);
37 private int huge = 0;
38 public void extractMethodsFromDirectory(final String directory,
39 final int maxStructuresAllowed, final int minStructuresAllowed,
40 final String outputPath, String outputFile)
41 throws FileNotFoundException, NoClassesFound, IOException,
42 IRException, FragmentParseException {
43
44 List < File > classFiles = new LinkedList < File >();
45 super.getClassFiles(new File(directory), classFiles);
46 if (classFiles.size() == 0) {
47 throw new NoClassesFound();
48 }
49 Iterator < File > it = classFiles.iterator();
50 HashMap < String, IntegerHolder > fragments = new HashMap < String, IntegerHolder >(100000);
51 int i = 0;
52 while (it.hasNext()) {
53 File f = it.next();
54
55
56
57 processClass(f, fragments, maxStructuresAllowed);
58 i++;
59 }
60
61
62 FileWriter output = new FileWriter(outputFile);
63 for (Map.Entry < String, IntegerHolder > entry : fragments.entrySet()) {
64 String treeStr = entry.getKey();
65 MTDFragmentAST tree = OBFragment.parseTree(treeStr);
66
67 if (tree.getSize() >= minStructuresAllowed
68 && tree.getSize() <= maxStructuresAllowed) {
69 output.write(entry.getValue().getValue() + "\t"
70 + entry.getKey() + "\n");
71 }
72 }
73 output.close();
74 }
75
76 protected String toString(FValue x, int max) throws HugeFragmentException{
77 StringBuilder treeTemp = new StringBuilder();
78 Set visited = new HashSet();
79 IntegerHolder count = new IntegerHolder(0);
80 x.toFragment(treeTemp, visited, count, max);
81 return treeTemp.toString();
82 }
83
84 protected void processClass(File f,
85 HashMap < String, IntegerHolder > fragments, int max) throws IOException {
86
87 FileInputStream read = new FileInputStream(f);
88
89 ClassReader cr = new ClassReader(new BufferedInputStream(
90 read));
91 read.close();
92 ClassNode cn = new ClassNode();
93 cr.accept(cn, ClassReader.SKIP_DEBUG);
94 List < MethodNode > methods = cn.methods;
95 Set expanded = new HashSet();
96 for (MethodNode m : methods) {
97 if (m.instructions.size() > 0) {
98 Analyzer a = new Analyzer(new FragmentInterpreter());
99 try {
100 a.analyze(cn.name, m);
101 } catch (Exception ignored) {
102 }
103 if (a.getFrames() != null) {
104 for (Frame frame : a.getFrames()) {
105 if (frame != null) {
106 int i = 0;
107 while (i < frame.getLocals()) {
108 Value val = frame.getLocal(i);
109
110 if (val instanceof FValue && ! expanded.contains(val)) {
111 try{
112 String fragment = toString(((FValue) val), max);
113
114 IntegerHolder multiplicity = fragments
115 .get(fragment);
116 if (multiplicity == null) {
117 multiplicity = new IntegerHolder(0);
118 fragments.put(fragment, multiplicity);
119 }
120 multiplicity.inc();
121 }catch(HugeFragmentException e){
122 huge++;
123 }
124 expanded.add(val);
125 }
126 i++;
127 }
128 }
129 }
130 }
131 }
132 }
133 }
134
135 }