Source Code Cross Referenced for SAXBugCollectionHandler.java in  » Code-Analyzer » findbugs » edu » umd » cs » findbugs » Java Source Code / Java DocumentationJava Source Code and Java Documentation

Java Source Code / Java Documentation
1. 6.0 JDK Core
2. 6.0 JDK Modules
3. 6.0 JDK Modules com.sun
4. 6.0 JDK Modules com.sun.java
5. 6.0 JDK Modules sun
6. 6.0 JDK Platform
7. Ajax
8. Apache Harmony Java SE
9. Aspect oriented
10. Authentication Authorization
11. Blogger System
12. Build
13. Byte Code
14. Cache
15. Chart
16. Chat
17. Code Analyzer
18. Collaboration
19. Content Management System
20. Database Client
21. Database DBMS
22. Database JDBC Connection Pool
23. Database ORM
24. Development
25. EJB Server geronimo
26. EJB Server GlassFish
27. EJB Server JBoss 4.2.1
28. EJB Server resin 3.1.5
29. ERP CRM Financial
30. ESB
31. Forum
32. GIS
33. Graphic Library
34. Groupware
35. HTML Parser
36. IDE
37. IDE Eclipse
38. IDE Netbeans
39. Installer
40. Internationalization Localization
41. Inversion of Control
42. Issue Tracking
43. J2EE
44. JBoss
45. JMS
46. JMX
47. Library
48. Mail Clients
49. Net
50. Parser
51. PDF
52. Portal
53. Profiler
54. Project Management
55. Report
56. RSS RDF
57. Rule Engine
58. Science
59. Scripting
60. Search Engine
61. Security
62. Sevlet Container
63. Source Control
64. Swing Library
65. Template Engine
66. Test Coverage
67. Testing
68. UML
69. Web Crawler
70. Web Framework
71. Web Mail
72. Web Server
73. Web Services
74. Web Services apache cxf 2.0.1
75. Web Services AXIS2
76. Wiki Engine
77. Workflow Engines
78. XML
79. XML UI
Java
Java Tutorial
Java Open Source
Jar File Download
Java Articles
Java Products
Java by API
Photoshop Tutorials
Maya Tutorials
Flash Tutorials
3ds-Max Tutorials
Illustrator Tutorials
GIMP Tutorials
C# / C Sharp
C# / CSharp Tutorial
C# / CSharp Open Source
ASP.Net
ASP.NET Tutorial
JavaScript DHTML
JavaScript Tutorial
JavaScript Reference
HTML / CSS
HTML CSS Reference
C / ANSI-C
C Tutorial
C++
C++ Tutorial
Ruby
PHP
Python
Python Tutorial
Python Open Source
SQL Server / T-SQL
SQL Server / T-SQL Tutorial
Oracle PL / SQL
Oracle PL/SQL Tutorial
PostgreSQL
SQL / MySQL
MySQL Tutorial
VB.Net
VB.Net Tutorial
Flash / Flex / ActionScript
VBA / Excel / Access / Word
XML
XML Tutorial
Microsoft Office PowerPoint 2007 Tutorial
Microsoft Office Excel 2007 Tutorial
Microsoft Office Word 2007 Tutorial
Java Source Code / Java Documentation » Code Analyzer » findbugs » edu.umd.cs.findbugs 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:         * FindBugs - Find bugs in Java programs
003:         * Copyright (C) 2004-2005 University of Maryland
004:         * 
005:         * This library is free software; you can redistribute it and/or
006:         * modify it under the terms of the GNU Lesser General Public
007:         * License as published by the Free Software Foundation; either
008:         * version 2.1 of the License, or (at your option) any later version.
009:         * 
010:         * This library is distributed in the hope that it will be useful,
011:         * but WITHOUT ANY WARRANTY; without even the implied warranty of
012:         * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
013:         * Lesser General Public License for more details.
014:         * 
015:         * You should have received a copy of the GNU Lesser General Public
016:         * License along with this library; if not, write to the Free Software
017:         * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
018:         */
019:
020:        package edu.umd.cs.findbugs;
021:
022:        import java.io.File;
023:        import java.util.ArrayList;
024:        import java.util.Stack;
025:        import java.util.regex.Pattern;
026:
027:        import org.xml.sax.Attributes;
028:        import org.xml.sax.SAXException;
029:        import org.xml.sax.helpers.DefaultHandler;
030:
031:        import edu.umd.cs.findbugs.ba.ClassHash;
032:        import edu.umd.cs.findbugs.filter.AndMatcher;
033:        import edu.umd.cs.findbugs.filter.BugMatcher;
034:        import edu.umd.cs.findbugs.filter.ClassMatcher;
035:        import edu.umd.cs.findbugs.filter.CompoundMatcher;
036:        import edu.umd.cs.findbugs.filter.DesignationMatcher;
037:        import edu.umd.cs.findbugs.filter.FieldMatcher;
038:        import edu.umd.cs.findbugs.filter.Filter;
039:        import edu.umd.cs.findbugs.filter.FirstVersionMatcher;
040:        import edu.umd.cs.findbugs.filter.LastVersionMatcher;
041:        import edu.umd.cs.findbugs.filter.LocalMatcher;
042:        import edu.umd.cs.findbugs.filter.Matcher;
043:        import edu.umd.cs.findbugs.filter.MethodMatcher;
044:        import edu.umd.cs.findbugs.filter.OrMatcher;
045:        import edu.umd.cs.findbugs.filter.PriorityMatcher;
046:        import edu.umd.cs.findbugs.model.ClassFeatureSet;
047:        import edu.umd.cs.findbugs.util.Strings;
048:
049:        /**
050:         * Build a BugCollection based on SAX events.
051:         * This is intended to replace the old DOM-based parsing
052:         * of XML bug result files, which was very slow.
053:         *
054:         * @author David Hovemeyer
055:         */
056:        public class SAXBugCollectionHandler extends DefaultHandler {
057:            /**
058:             * 
059:             */
060:            private static final String FIND_BUGS_FILTER = "FindBugsFilter";
061:            /**
062:             * 
063:             */
064:            private static final String PROJECT = "Project";
065:            /**
066:             * 
067:             */
068:            private static final String BUG_COLLECTION = "BugCollection";
069:            private BugCollection bugCollection;
070:            private Project project;
071:            private Stack<CompoundMatcher> matcherStack = new Stack<CompoundMatcher>();
072:            private Filter filter;
073:
074:            private ArrayList<String> elementStack;
075:            private StringBuffer textBuffer;
076:            private BugInstance bugInstance;
077:            private PackageMemberAnnotation packageMemberAnnotation;
078:            private AnalysisError analysisError;
079:            //	private ClassHash classHash;
080:            private ClassFeatureSet classFeatureSet;
081:            private ArrayList<String> stackTrace;
082:            private int nestingOfIgnoredElements = 0;
083:            private final File base;
084:            private final String topLevelName;
085:
086:            public SAXBugCollectionHandler(String topLevelName,
087:                    BugCollection bugCollection, Project project, File base) {
088:                this .topLevelName = topLevelName;
089:                this .bugCollection = bugCollection;
090:                this .project = project;
091:
092:                this .elementStack = new ArrayList<String>();
093:                this .textBuffer = new StringBuffer();
094:                this .stackTrace = new ArrayList<String>();
095:                this .base = base;
096:
097:            }
098:
099:            public SAXBugCollectionHandler(BugCollection bugCollection,
100:                    Project project, File base) {
101:                this (BUG_COLLECTION, bugCollection, project, base);
102:            }
103:
104:            public SAXBugCollectionHandler(Project project, File base) {
105:                this (PROJECT, null, project, base);
106:            }
107:
108:            public SAXBugCollectionHandler(Filter filter, File base) {
109:                this (FIND_BUGS_FILTER, null, null, base);
110:                this .filter = filter;
111:                pushCompoundMatcher(filter);
112:            }
113:
114:            Pattern ignoredElement = Pattern
115:                    .compile("Message|ShortMessage|LongMessage");
116:
117:            public boolean discardedElement(String qName) {
118:                return ignoredElement.matcher(qName).matches();
119:
120:            }
121:
122:            private static boolean DEBUG = false;
123:
124:            @Override
125:            public void startElement(String uri, String name, String qName,
126:                    Attributes attributes) throws SAXException {
127:                // URI should always be empty.
128:                // So, qName is the name of the element.
129:
130:                if (discardedElement(qName)) {
131:                    nestingOfIgnoredElements++;
132:                } else if (nestingOfIgnoredElements > 0) {
133:                    // ignore it
134:                } else {
135:                    // We should be parsing the outer BugCollection element.
136:                    if (elementStack.isEmpty() && !qName.equals(topLevelName))
137:                        throw new SAXException(
138:                                "Invalid top-level element (expected "
139:                                        + topLevelName + ", saw " + qName + ")");
140:
141:                    if (qName.equals(BUG_COLLECTION)) {
142:                        // Read and set the sequence number.
143:                        String version = attributes.getValue("version");
144:                        if (bugCollection instanceof  SortedBugCollection)
145:                            ((SortedBugCollection) bugCollection)
146:                                    .setAnalysisVersion(version);
147:
148:                        // Read and set the sequence number.
149:                        String sequence = attributes.getValue("sequence");
150:                        long seqval = parseLong(sequence, 0L);
151:                        bugCollection.setSequenceNumber(seqval);
152:
153:                        // Read and set timestamp.
154:                        String timestamp = attributes.getValue("timestamp");
155:                        long tsval = parseLong(timestamp, -1L);
156:                        bugCollection.setTimestamp(tsval);
157:                        // Read and set timestamp.
158:                        String analysisTimestamp = attributes
159:                                .getValue("analysisTimestamp");
160:                        if (analysisTimestamp != null) {
161:                            bugCollection.setAnalysisTimestamp(parseLong(
162:                                    analysisTimestamp, -1L));
163:                        }
164:
165:                        // Set release name, if present.
166:                        String releaseName = attributes.getValue("release");
167:                        bugCollection
168:                                .setReleaseName((releaseName != null) ? releaseName
169:                                        : "");
170:                    } else if (isTopLevelFilter(qName)) {
171:                        if (project != null) {
172:                            filter = new Filter();
173:                            project.setSuppressionFilter(filter);
174:                        }
175:                        matcherStack.clear();
176:                        pushCompoundMatcher(filter);
177:                    } else if (qName.equals(PROJECT)) {
178:                        // Project element
179:                        String filename = attributes
180:                                .getValue(Project.FILENAME_ATTRIBUTE_NAME);
181:                        if (filename != null)
182:                            project.setProjectFileName(filename);
183:                        String projectName = attributes
184:                                .getValue(Project.PROJECTNAME_ATTRIBUTE_NAME);
185:                        if (projectName != null)
186:                            project.setProjectName(projectName);
187:                    } else {
188:                        String outerElement = elementStack.get(elementStack
189:                                .size() - 1);
190:                        if (outerElement.equals(BUG_COLLECTION)) {
191:                            // Parsing a top-level element of the BugCollection
192:                            if (qName.equals("BugInstance")) {
193:                                // BugInstance element - get required type and priority attributes
194:                                String type = getRequiredAttribute(attributes,
195:                                        "type", qName);
196:                                String priority = getRequiredAttribute(
197:                                        attributes, "priority", qName);
198:
199:                                try {
200:                                    int prio = Integer.parseInt(priority);
201:                                    bugInstance = new BugInstance(type, prio);
202:                                } catch (NumberFormatException e) {
203:                                    throw new SAXException(
204:                                            "BugInstance with invalid priority value \""
205:                                                    + priority + "\"", e);
206:                                }
207:
208:                                String uniqueId = attributes.getValue("uid");
209:                                if (uniqueId != null) {
210:                                    bugInstance.setUniqueId(uniqueId);
211:                                }
212:
213:                                String firstVersion = attributes
214:                                        .getValue("first");
215:                                if (firstVersion != null) {
216:                                    bugInstance.setFirstVersion(Long
217:                                            .parseLong(firstVersion));
218:                                }
219:                                String lastVersion = attributes
220:                                        .getValue("last");
221:                                if (lastVersion != null) {
222:                                    bugInstance.setLastVersion(Long
223:                                            .parseLong(lastVersion));
224:                                }
225:
226:                                if (bugInstance.getLastVersion() >= 0
227:                                        && bugInstance.getFirstVersion() > bugInstance
228:                                                .getLastVersion())
229:                                    throw new IllegalStateException("huh");
230:
231:                                String introducedByChange = attributes
232:                                        .getValue("introducedByChange");
233:                                if (introducedByChange != null) {
234:                                    bugInstance
235:                                            .setIntroducedByChangeOfExistingClass(TigerSubstitutes
236:                                                    .parseBoolean(introducedByChange));
237:                                }
238:                                String removedByChange = attributes
239:                                        .getValue("removedByChange");
240:                                if (removedByChange != null) {
241:                                    bugInstance
242:                                            .setRemovedByChangeOfPersistingClass(TigerSubstitutes
243:                                                    .parseBoolean(removedByChange));
244:                                }
245:                                String oldInstanceHash = attributes
246:                                        .getValue("instanceHash");
247:                                if (oldInstanceHash != null) {
248:                                    bugInstance
249:                                            .setOldInstanceHash(oldInstanceHash);
250:                                }
251:
252:                            } else if (qName.equals("FindBugsSummary")) {
253:                                String timestamp = getRequiredAttribute(
254:                                        attributes, "timestamp", qName);
255:                                try {
256:                                    bugCollection.getProjectStats()
257:                                            .setTimestamp(timestamp);
258:                                } catch (java.text.ParseException e) {
259:                                    throw new SAXException(
260:                                            "Unparseable sequence number: '"
261:                                                    + timestamp + "'", e);
262:                                }
263:                            }
264:                        } else if (outerElement.equals("BugInstance")) {
265:                            parseBugInstanceContents(qName, attributes);
266:                        } else if (outerElement.equals("Method")
267:                                || outerElement.equals("Field")
268:                                || outerElement.equals("Class")) {
269:                            if (qName.equals("SourceLine")) {
270:                                // package member elements can contain nested SourceLine elements.
271:                                packageMemberAnnotation
272:                                        .setSourceLines(createSourceLineAnnotation(
273:                                                qName, attributes));
274:                            }
275:                        } else if (outerElement
276:                                .equals(BugCollection.ERRORS_ELEMENT_NAME)) {
277:                            if (qName
278:                                    .equals(BugCollection.ANALYSIS_ERROR_ELEMENT_NAME)
279:                                    || qName
280:                                            .equals(BugCollection.ERROR_ELEMENT_NAME)) {
281:                                analysisError = new AnalysisError(
282:                                        "Unknown error");
283:                                stackTrace.clear();
284:                            }
285:                        } else if (outerElement.equals("PackageStats")) {
286:                            if (qName.equals("ClassStats")) {
287:                                String className = getRequiredAttribute(
288:                                        attributes, "class", qName);
289:                                Boolean isInterface = Boolean
290:                                        .valueOf(getRequiredAttribute(
291:                                                attributes, "interface", qName));
292:                                int size = Integer
293:                                        .valueOf(getRequiredAttribute(
294:                                                attributes, "size", qName));
295:                                String sourceFile = attributes
296:                                        .getValue("sourceFile");
297:                                bugCollection.getProjectStats().addClass(
298:                                        className, sourceFile, isInterface,
299:                                        size);
300:                            }
301:
302:                        } else if (isTopLevelFilter(outerElement)
303:                                || outerElement.equals("Match")
304:                                || outerElement.equals("And")
305:                                || outerElement.equals("Or")) {
306:                            parseMatcher(qName, attributes);
307:                        } else if (outerElement.equals("ClassFeatures")) {
308:                            if (qName.equals(ClassFeatureSet.ELEMENT_NAME)) {
309:                                String className = getRequiredAttribute(
310:                                        attributes, "class", qName);
311:                                classFeatureSet = new ClassFeatureSet();
312:                                classFeatureSet.setClassName(className);
313:                            }
314:                        } else if (outerElement
315:                                .equals(ClassFeatureSet.ELEMENT_NAME)) {
316:                            if (qName
317:                                    .equals(ClassFeatureSet.FEATURE_ELEMENT_NAME)) {
318:                                String value = getRequiredAttribute(attributes,
319:                                        "value", qName);
320:                                classFeatureSet.addFeature(value);
321:                            }
322:                        } else if (outerElement
323:                                .equals(BugCollection.HISTORY_ELEMENT_NAME)) {
324:                            if (qName.equals(AppVersion.ELEMENT_NAME)) {
325:                                try {
326:                                    String sequence = getRequiredAttribute(
327:                                            attributes, "sequence", qName);
328:                                    String timestamp = attributes
329:                                            .getValue("timestamp");
330:                                    String releaseName = attributes
331:                                            .getValue("release");
332:                                    String codeSize = attributes
333:                                            .getValue("codeSize");
334:                                    String numClasses = attributes
335:                                            .getValue("numClasses");
336:                                    AppVersion appVersion = new AppVersion(Long
337:                                            .valueOf(sequence));
338:                                    if (timestamp != null)
339:                                        appVersion.setTimestamp(Long
340:                                                .valueOf(timestamp));
341:                                    if (releaseName != null)
342:                                        appVersion.setReleaseName(releaseName);
343:                                    if (codeSize != null)
344:                                        appVersion.setCodeSize(Integer
345:                                                .parseInt(codeSize));
346:                                    if (numClasses != null)
347:                                        appVersion.setNumClasses(Integer
348:                                                .parseInt(numClasses));
349:
350:                                    bugCollection.addAppVersion(appVersion);
351:                                } catch (NumberFormatException e) {
352:                                    throw new SAXException(
353:                                            "Invalid AppVersion element", e);
354:                                }
355:                            }
356:                        }
357:                    }
358:                }
359:
360:                textBuffer.delete(0, textBuffer.length());
361:                elementStack.add(qName);
362:            }
363:
364:            private boolean isTopLevelFilter(String qName) {
365:                return qName.equals(FIND_BUGS_FILTER)
366:                        || qName.equals("SuppressionFilter");
367:            }
368:
369:            private void addMatcher(Matcher m) {
370:                if (m == null)
371:                    throw new IllegalArgumentException(
372:                            "matcher must not be null");
373:
374:                CompoundMatcher peek = matcherStack.peek();
375:                if (peek == null)
376:                    throw new NullPointerException("Top of stack is null");
377:                peek.addChild(m);
378:                if (nextMatchedIsDisabled) {
379:                    if (peek instanceof  Filter)
380:                        ((Filter) peek).disable(m);
381:                    else
382:                        assert false;
383:                    nextMatchedIsDisabled = false;
384:                }
385:            }
386:
387:            private void pushCompoundMatcherAsChild(CompoundMatcher m) {
388:                addMatcher(m);
389:                pushCompoundMatcher(m);
390:            }
391:
392:            private void pushCompoundMatcher(CompoundMatcher m) {
393:                if (m == null)
394:                    throw new IllegalArgumentException(
395:                            "matcher must not be null");
396:                matcherStack.push(m);
397:            }
398:
399:            boolean nextMatchedIsDisabled;
400:
401:            private void parseMatcher(String qName, Attributes attributes)
402:                    throws SAXException {
403:                if (DEBUG)
404:                    System.out.println(elementStack + " " + qName + " "
405:                            + matcherStack);
406:                String disabled = attributes.getValue("disabled");
407:                nextMatchedIsDisabled = "true".equals(disabled);
408:                if (qName.equals("Bug")) {
409:                    addMatcher(new BugMatcher(attributes.getValue("code"),
410:                            attributes.getValue("pattern"), attributes
411:                                    .getValue("category")));
412:                } else if (qName.equals("Class")) {
413:                    addMatcher(new ClassMatcher(attributes.getValue("name")));
414:                } else if (qName.equals("FirstVersion")) {
415:                    addMatcher(new FirstVersionMatcher(getRequiredAttribute(
416:                            attributes, "value", qName), getRequiredAttribute(
417:                            attributes, "relOp", qName)));
418:                } else if (qName.equals("LastVersion")) {
419:                    addMatcher(new LastVersionMatcher(getRequiredAttribute(
420:                            attributes, "value", qName), getRequiredAttribute(
421:                            attributes, "relOp", qName)));
422:                } else if (qName.equals("Designation")) {
423:                    addMatcher(new DesignationMatcher(getRequiredAttribute(
424:                            attributes, "designation", qName)));
425:                } else if (qName.equals("BugCode")) {
426:                    addMatcher(new BugMatcher(attributes.getValue("name"), "",
427:                            ""));
428:                } else if (qName.equals("Local")) {
429:                    addMatcher(new LocalMatcher(attributes.getValue("name")));
430:                } else if (qName.equals("BugPattern")) {
431:                    addMatcher(new BugMatcher("", attributes.getValue("name"),
432:                            ""));
433:                } else if (qName.equals("Priority")) {
434:                    addMatcher(new PriorityMatcher(attributes.getValue("value")));
435:                } else if (qName.equals("Package")) {
436:                    String pName = attributes.getValue("name");
437:                    pName = pName.startsWith("~") ? pName : "~"
438:                            + Strings.replace(pName, ".", "\\.");
439:                    addMatcher(new ClassMatcher(pName + "\\.[^.]+"));
440:                } else if (qName.equals("Method")) {
441:                    String name = attributes.getValue("name");
442:                    String params = attributes.getValue("params");
443:                    String returns = attributes.getValue("returns");
444:                    addMatcher(new MethodMatcher(name, params, returns));
445:                } else if (qName.equals("Field")) {
446:                    String name = attributes.getValue("name");
447:                    String type = attributes.getValue("type");
448:                    addMatcher(new FieldMatcher(name, type));
449:                } else if (qName.equals("Or")) {
450:                    CompoundMatcher matcher = new OrMatcher();
451:                    pushCompoundMatcherAsChild(matcher);
452:                } else if (qName.equals("And") || qName.equals("Match")) {
453:                    AndMatcher matcher = new AndMatcher();
454:                    pushCompoundMatcherAsChild(matcher);
455:                    if (qName.equals("Match")) {
456:                        String classregex = attributes.getValue("classregex");
457:                        String classMatch = attributes.getValue("class");
458:
459:                        if (classregex != null)
460:                            addMatcher(new ClassMatcher("~" + classregex));
461:                        else if (classMatch != null)
462:                            addMatcher(new ClassMatcher(classMatch));
463:                    }
464:                }
465:                nextMatchedIsDisabled = false;
466:            }
467:
468:            private void parseBugInstanceContents(String qName,
469:                    Attributes attributes) throws SAXException {
470:                // Parsing an attribute or property of a BugInstance
471:                BugAnnotation bugAnnotation = null;
472:                if (qName.equals("Class")) {
473:                    String className = getRequiredAttribute(attributes,
474:                            "classname", qName);
475:                    bugAnnotation = packageMemberAnnotation = new ClassAnnotation(
476:                            className);
477:                } else if (qName.equals("Type")) {
478:                    String typeDescriptor = getRequiredAttribute(attributes,
479:                            "descriptor", qName);
480:                    bugAnnotation = new TypeAnnotation(typeDescriptor);
481:                } else if (qName.equals("Method") || qName.equals("Field")) {
482:                    String classname = getRequiredAttribute(attributes,
483:                            "classname", qName);
484:                    String fieldOrMethodName = getRequiredAttribute(attributes,
485:                            "name", qName);
486:                    String signature = getRequiredAttribute(attributes,
487:                            "signature", qName);
488:                    if (qName.equals("Method")) {
489:                        String isStatic = attributes.getValue("isStatic");
490:                        if (isStatic == null) {
491:                            isStatic = "false"; // Hack for old data
492:                        }
493:
494:                        bugAnnotation = packageMemberAnnotation = new MethodAnnotation(
495:                                classname, fieldOrMethodName, signature,
496:                                Boolean.valueOf(isStatic));
497:
498:                    } else {
499:                        String isStatic = getRequiredAttribute(attributes,
500:                                "isStatic", qName);
501:                        bugAnnotation = packageMemberAnnotation = new FieldAnnotation(
502:                                classname, fieldOrMethodName, signature,
503:                                Boolean.valueOf(isStatic));
504:                    }
505:
506:                } else if (qName.equals("SourceLine")) {
507:                    SourceLineAnnotation sourceAnnotation = createSourceLineAnnotation(
508:                            qName, attributes);
509:                    if (!sourceAnnotation.isSynthetic())
510:                        bugAnnotation = sourceAnnotation;
511:                } else if (qName.equals("Int")) {
512:                    try {
513:                        String value = getRequiredAttribute(attributes,
514:                                "value", qName);
515:                        bugAnnotation = new IntAnnotation(Integer
516:                                .parseInt(value));
517:                    } catch (NumberFormatException e) {
518:                        throw new SAXException("Bad integer value in Int");
519:                    }
520:                } else if (qName.equals("String")) {
521:                    String value = getRequiredAttribute(attributes, "value",
522:                            qName);
523:                    bugAnnotation = new StringAnnotation(value);
524:                } else if (qName.equals("LocalVariable")) {
525:                    try {
526:                        String varName = getRequiredAttribute(attributes,
527:                                "name", qName);
528:                        int register = Integer.parseInt(getRequiredAttribute(
529:                                attributes, "register", qName));
530:                        int pc = Integer.parseInt(getRequiredAttribute(
531:                                attributes, "pc", qName));
532:                        bugAnnotation = new LocalVariableAnnotation(varName,
533:                                register, pc);
534:                    } catch (NumberFormatException e) {
535:                        throw new SAXException(
536:                                "Invalid integer value in attribute of LocalVariable element");
537:                    }
538:                } else if (qName.equals("Property")) {
539:                    // A BugProperty.
540:                    String propName = getRequiredAttribute(attributes, "name",
541:                            qName);
542:                    String propValue = getRequiredAttribute(attributes,
543:                            "value", qName);
544:                    bugInstance.setProperty(propName, propValue);
545:                } else if (qName.equals("UserAnnotation")) {
546:                    // ignore AnnotationText for now; will handle in endElement
547:                    String s = attributes.getValue("designation"); // optional
548:                    BugDesignation userDesignation = bugInstance
549:                            .getNonnullUserDesignation();
550:                    if (s != null)
551:                        userDesignation.setDesignationKey(s);
552:                    s = attributes.getValue("user"); // optional
553:                    if (s != null)
554:                        userDesignation.setUser(s);
555:                    s = attributes.getValue("timestamp"); // optional
556:                    if (s != null)
557:                        try {
558:                            long timestamp = Long.valueOf(s);
559:                            userDesignation.setTimestamp(timestamp);
560:                        } catch (NumberFormatException nfe) {
561:                            // ok to contine -- just won't set a timestamp for the user designation.
562:                            // but is there anyplace to report this?
563:                        }
564:                } else
565:                    throw new SAXException("Unknown bug annotation named "
566:                            + qName);
567:
568:                if (bugAnnotation != null) {
569:                    String role = attributes.getValue("role");
570:                    if (role != null)
571:                        bugAnnotation.setDescription(role);
572:                    setAnnotationRole(attributes, bugAnnotation);
573:                    bugInstance.add(bugAnnotation);
574:                }
575:            }
576:
577:            private long parseLong(String s, long defaultValue) {
578:                long value;
579:                try {
580:                    value = (s != null) ? Long.parseLong(s) : defaultValue;
581:                } catch (NumberFormatException e) {
582:                    value = defaultValue;
583:                }
584:                return value;
585:            }
586:
587:            /**
588:             * Extract a hash value from an element.
589:             * 
590:             * @param qName      name of element containing hash value
591:             * @param attributes element attributes
592:             * @return the decoded hash value
593:             * @throws SAXException
594:             */
595:            private byte[] extractHash(String qName, Attributes attributes)
596:                    throws SAXException {
597:                String encodedHash = getRequiredAttribute(attributes, "value",
598:                        qName);
599:                byte[] hash;
600:                try {
601:                    //System.out.println("Extract hash " + encodedHash);
602:                    hash = ClassHash.stringToHash(encodedHash);
603:                } catch (IllegalArgumentException e) {
604:                    throw new SAXException("Invalid class hash", e);
605:                }
606:                return hash;
607:            }
608:
609:            private void setAnnotationRole(Attributes attributes,
610:                    BugAnnotation bugAnnotation) {
611:                String role = attributes.getValue("role");
612:                if (role != null)
613:                    bugAnnotation.setDescription(role);
614:            }
615:
616:            private SourceLineAnnotation createSourceLineAnnotation(
617:                    String qName, Attributes attributes) throws SAXException {
618:                String classname = getRequiredAttribute(attributes,
619:                        "classname", qName);
620:                String sourceFile = attributes.getValue("sourcefile");
621:                if (sourceFile == null)
622:                    sourceFile = SourceLineAnnotation.UNKNOWN_SOURCE_FILE;
623:                String startLine = attributes.getValue("start"); // "start"/"end" are now optional
624:                String endLine = attributes.getValue("end"); // (were too many "-1"s in the xml)
625:                String startBytecode = attributes.getValue("startBytecode");
626:                String endBytecode = attributes.getValue("endBytecode");
627:
628:                try {
629:                    int sl = startLine != null ? Integer.parseInt(startLine)
630:                            : -1;
631:                    int el = endLine != null ? Integer.parseInt(endLine) : -1;
632:                    int sb = startBytecode != null ? Integer
633:                            .parseInt(startBytecode) : -1;
634:                    int eb = endBytecode != null ? Integer
635:                            .parseInt(endBytecode) : -1;
636:
637:                    SourceLineAnnotation annotation = new SourceLineAnnotation(
638:                            classname, sourceFile, sl, el, sb, eb);
639:
640:                    return annotation;
641:                } catch (NumberFormatException e) {
642:                    throw new SAXException(
643:                            "Bad integer value in SourceLine element", e);
644:                }
645:            }
646:
647:            @Override
648:            public void endElement(String uri, String name, String qName)
649:                    throws SAXException {
650:                // URI should always be empty.
651:                // So, qName is the name of the element.
652:
653:                if (discardedElement(qName)) {
654:                    nestingOfIgnoredElements--;
655:                } else if (nestingOfIgnoredElements > 0) {
656:                    // ignore it
657:                } else if (elementStack.size() > 1) {
658:                    String outerElement = elementStack
659:                            .get(elementStack.size() - 2);
660:
661:                    if (qName.equals("Or") || qName.equals("And")
662:                            || qName.equals("Match") || isTopLevelFilter(qName)) {
663:                        if (DEBUG)
664:                            System.out.println("  ending " + elementStack + " "
665:                                    + qName + " " + matcherStack);
666:
667:                        matcherStack.pop();
668:                    } else if (outerElement.equals(BUG_COLLECTION)) {
669:                        if (qName.equals("BugInstance")) {
670:                            bugCollection.add(bugInstance, false);
671:                            // TODO: check this
672:                            if (bugInstance.getLastVersion() == -1)
673:                                bugCollection.getProjectStats().addBug(
674:                                        bugInstance);
675:                        }
676:                    } else if (outerElement.equals(PROJECT)) {
677:                        //System.out.println("Adding project element " + qName + ": " + textBuffer.toString());
678:                        if (qName.equals("Jar"))
679:                            project.addFile(textBuffer.toString());
680:                        else if (qName.equals("SrcDir"))
681:                            project.addSourceDir(textBuffer.toString());
682:                        else if (qName.equals("AuxClasspathEntry"))
683:                            project.addAuxClasspathEntry(textBuffer.toString());
684:                    } else if (outerElement.equals("BugInstance")) {
685:                        if (qName.equals("UserAnnotation")) {
686:                            bugInstance
687:                                    .setAnnotationText(textBuffer.toString());
688:                        }
689:                    } else if (outerElement
690:                            .equals(BugCollection.ERRORS_ELEMENT_NAME)) {
691:                        if (qName
692:                                .equals(BugCollection.ANALYSIS_ERROR_ELEMENT_NAME)) {
693:                            analysisError.setMessage(textBuffer.toString());
694:                            bugCollection.addError(analysisError);
695:                        } else if (qName
696:                                .equals(BugCollection.ERROR_ELEMENT_NAME)) {
697:                            if (stackTrace.size() > 0) {
698:                                analysisError
699:                                        .setStackTrace(stackTrace
700:                                                .toArray(new String[stackTrace
701:                                                        .size()]));
702:                            }
703:                            bugCollection.addError(analysisError);
704:                        } else if (qName
705:                                .equals(BugCollection.MISSING_CLASS_ELEMENT_NAME)) {
706:                            bugCollection
707:                                    .addMissingClass(textBuffer.toString());
708:                        }
709:
710:                    } else if (outerElement
711:                            .equals(BugCollection.ERROR_ELEMENT_NAME)) {
712:                        if (qName
713:                                .equals(BugCollection.ERROR_MESSAGE_ELEMENT_NAME)) {
714:                            analysisError.setMessage(textBuffer.toString());
715:                        } else if (qName
716:                                .equals(BugCollection.ERROR_EXCEPTION_ELEMENT_NAME)) {
717:                            analysisError.setExceptionMessage(textBuffer
718:                                    .toString());
719:                        } else if (qName
720:                                .equals(BugCollection.ERROR_STACK_TRACE_ELEMENT_NAME)) {
721:                            stackTrace.add(textBuffer.toString());
722:                        }
723:                    } else if (outerElement.equals("ClassFeatures")) {
724:                        if (qName.equals(ClassFeatureSet.ELEMENT_NAME)) {
725:                            bugCollection.setClassFeatureSet(classFeatureSet);
726:                            classFeatureSet = null;
727:                        }
728:                    }
729:                }
730:
731:                elementStack.remove(elementStack.size() - 1);
732:            }
733:
734:            @Override
735:            public void characters(char[] ch, int start, int length) {
736:                textBuffer.append(ch, start, length);
737:            }
738:
739:            private static String getRequiredAttribute(Attributes attributes,
740:                    String attrName, String elementName) throws SAXException {
741:                String value = attributes.getValue(attrName);
742:                if (value == null)
743:                    throw new SAXException(elementName + " element missing "
744:                            + attrName + " attribute");
745:                return value;
746:            }
747:
748:        }
749:
750:        // vim:ts=4
www.java2java.com | Contact Us
Copyright 2009 - 12 Demo Source and Support. All rights reserved.
All other trademarks are property of their respective owners.