1 package org.softevo.jdynpur.eval;
2
3 import java.io.File;
4 import java.io.FileInputStream;
5 import java.io.IOException;
6 import java.io.InputStream;
7 import java.util.HashMap;
8 import java.util.HashSet;
9
10 import org.xml.sax.Attributes;
11 import org.xml.sax.InputSource;
12 import org.xml.sax.SAXException;
13 import org.xml.sax.XMLReader;
14 import org.xml.sax.helpers.DefaultHandler;
15 import org.xml.sax.helpers.XMLReaderFactory;
16
17 public class JDynpurResultsFileParser {
18
19 public static HashMap<String, HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier>> parse(File file) throws SAXException, IOException {
20 return parse(new FileInputStream(file));
21 }
22
23 public static HashMap<String, HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier>> parse(InputStream inputStream) throws SAXException, IOException {
24 XMLReader parser = XMLReaderFactory.createXMLReader();
25 ParseHandler handler = new ParseHandler();
26 parser.setContentHandler(handler);
27 InputSource inputSource = new InputSource(inputStream);
28 parser.parse(inputSource);
29 return handler.identifiers;
30 }
31
32 private static class ParseHandler extends DefaultHandler {
33
34 public static final int ST_EXECUTED = 1;
35
36 public static final int ST_IMPURE = 2;
37
38 public static final int ST_PURE = 3;
39
40 public static final int ST_PARAMETER = 4;
41
42 public static final int ST_MODIFIESSELF = 5;
43
44 private static int state = 0;
45
46 public HashMap<String, HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier>> identifiers = new HashMap<String, HashMap<ExtendedMethodIdentifier,ExtendedMethodIdentifier>>();
47
48 private ExtendedMethodIdentifier identifierForParameters = null;
49
50
51 private HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier> getOrCreateSetForClass(String className) {
52 HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier> result = identifiers.get(className);
53 if (result == null) {
54 result = new HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier>();
55 identifiers.put(className, result);
56 }
57 return result;
58 }
59
60 @Override
61 public void startElement(String uri, String localName, String qName, Attributes attributes) throws SAXException {
62 if (localName.equalsIgnoreCase("executedmethods")) {
63 state = ST_EXECUTED;
64 } else if (localName.equalsIgnoreCase("impuremethods")) {
65 state = ST_IMPURE;
66 } else if (localName.equalsIgnoreCase("puremethods")) {
67 state = ST_PURE;
68 } else if (localName.equalsIgnoreCase("parametermutability")) {
69 state = ST_PARAMETER;
70 } else if (localName.equalsIgnoreCase("methodsmodifyingself")) {
71 state = ST_MODIFIESSELF;
72 } else if (localName.equals("method")){
73 String className = attributes.getValue("classname");
74 String methodName = attributes.getValue("methodname");
75 String signature = attributes.getValue("signature");
76 int access = Integer.parseInt(attributes.getValue("access"));
77 if (state == ST_IMPURE) {
78 ExtendedMethodIdentifier identifier = new ExtendedMethodIdentifier(className, methodName, signature, ExtendedMethodIdentifier.IMPURE, new HashSet<Integer>(), new HashSet<Integer>());
79 HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier> identifiers = getOrCreateSetForClass(className);
80 assert (!identifiers.containsKey(identifier)) : "Duplicate entry for identifier " + identifier;
81 identifiers.put(identifier, identifier);
82 } else if (state == ST_PURE) {
83 ExtendedMethodIdentifier identifier = new ExtendedMethodIdentifier(className, methodName, signature, ExtendedMethodIdentifier.PURE, new HashSet<Integer>(), new HashSet<Integer>());
84 HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier> identifiers = getOrCreateSetForClass(className);
85 assert (!identifiers.containsKey(identifier)) : "Duplicate entry for identifier " + identifier;
86 identifiers.put(identifier, identifier);
87 } else if (state == ST_MODIFIESSELF) {
88 if (methodName.equals("<init>")) {
89 ExtendedMethodIdentifier identifier = new ExtendedMethodIdentifier(className, methodName, signature, ExtendedMethodIdentifier.PURE, new HashSet<Integer>(), new HashSet<Integer>());
90 HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier> identifiers = getOrCreateSetForClass(className);
91 assert (!identifiers.containsKey(identifier)) : "Duplicate entry for identifier " + identifier;
92 identifiers.put(identifier, identifier);
93 }
94 } else if (state == ST_PARAMETER) {
95 ExtendedMethodIdentifier identifier = new ExtendedMethodIdentifier(className, methodName, signature, ExtendedMethodIdentifier.PURE, new HashSet<Integer>(), new HashSet<Integer>());
96 HashMap<ExtendedMethodIdentifier, ExtendedMethodIdentifier> identifiers = getOrCreateSetForClass(className);
97
98 if (!identifiers.containsKey(identifier)) {
99 identifiers.put(identifier, identifier);
100 }
101 identifierForParameters = identifiers.get(identifier);
102 }
103 } else if (localName.equals("parameter")) {
104 if (attributes.getValue("unmodified").equalsIgnoreCase("true")) {
105 identifierForParameters.addImutableParameter(Integer.parseInt(attributes.getValue("index")));
106 } else {
107 identifierForParameters.addMutableParameter(Integer.parseInt(attributes.getValue("index")));
108 }
109 }
110 }
111 }
112
113 public static void main(String[] args) throws SAXException, IOException {
114 File traceFile = new File("/Users/dallmeier/tmp/passing_675.xml");
115 parse(traceFile);
116 }
117 }