Source Code Cross Referenced for IsNullValueFrameModelingVisitor.java in  » Code-Analyzer » findbugs » edu » umd » cs » findbugs » ba » npe » 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.ba.npe 
Source Cross Referenced  Class Diagram Java Document (Java Doc) 


001:        /*
002:         * Bytecode Analysis Framework
003:         * Copyright (C) 2003-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.ba.npe;
021:
022:        import java.util.Map;
023:
024:        import org.apache.bcel.generic.ACONST_NULL;
025:        import org.apache.bcel.generic.ANEWARRAY;
026:        import org.apache.bcel.generic.CHECKCAST;
027:        import org.apache.bcel.generic.ConstantPoolGen;
028:        import org.apache.bcel.generic.GETFIELD;
029:        import org.apache.bcel.generic.GETSTATIC;
030:        import org.apache.bcel.generic.INVOKEINTERFACE;
031:        import org.apache.bcel.generic.INVOKESPECIAL;
032:        import org.apache.bcel.generic.INVOKESTATIC;
033:        import org.apache.bcel.generic.INVOKEVIRTUAL;
034:        import org.apache.bcel.generic.Instruction;
035:        import org.apache.bcel.generic.InvokeInstruction;
036:        import org.apache.bcel.generic.LDC;
037:        import org.apache.bcel.generic.LDC2_W;
038:        import org.apache.bcel.generic.MULTIANEWARRAY;
039:        import org.apache.bcel.generic.NEW;
040:        import org.apache.bcel.generic.NEWARRAY;
041:        import org.apache.bcel.generic.PUTFIELD;
042:        import org.apache.bcel.generic.ReferenceType;
043:        import org.apache.bcel.generic.Type;
044:
045:        import edu.umd.cs.findbugs.SystemProperties;
046:        import edu.umd.cs.findbugs.ba.AbstractFrameModelingVisitor;
047:        import edu.umd.cs.findbugs.ba.AnalysisContext;
048:        import edu.umd.cs.findbugs.ba.AssertionMethods;
049:        import edu.umd.cs.findbugs.ba.DataflowAnalysisException;
050:        import edu.umd.cs.findbugs.ba.NullnessAnnotation;
051:        import edu.umd.cs.findbugs.ba.XFactory;
052:        import edu.umd.cs.findbugs.ba.XField;
053:        import edu.umd.cs.findbugs.ba.XMethod;
054:        import edu.umd.cs.findbugs.ba.vna.AvailableLoad;
055:        import edu.umd.cs.findbugs.ba.vna.ValueNumber;
056:        import edu.umd.cs.findbugs.ba.vna.ValueNumberAnalysisFeatures;
057:        import edu.umd.cs.findbugs.ba.vna.ValueNumberDataflow;
058:        import edu.umd.cs.findbugs.ba.vna.ValueNumberFrame;
059:
060:        public class IsNullValueFrameModelingVisitor extends
061:                AbstractFrameModelingVisitor<IsNullValue, IsNullValueFrame> {
062:
063:            private static final boolean NO_ASSERT_HACK = SystemProperties
064:                    .getBoolean("inva.noAssertHack");
065:            private static final boolean MODEL_NONNULL_RETURN = SystemProperties
066:                    .getBoolean("fnd.modelNonnullReturn", true);
067:            private AssertionMethods assertionMethods;
068:            private ValueNumberDataflow vnaDataflow;
069:            private final boolean trackValueNumbers;
070:            private int slotContainingNewNullValue;
071:
072:            public IsNullValueFrameModelingVisitor(ConstantPoolGen cpg,
073:                    AssertionMethods assertionMethods,
074:                    ValueNumberDataflow vnaDataflow, boolean trackValueNumbers) {
075:                super (cpg);
076:                this .assertionMethods = assertionMethods;
077:                this .vnaDataflow = vnaDataflow;
078:                this .trackValueNumbers = trackValueNumbers;
079:            }
080:
081:            /* (non-Javadoc)
082:             * @see edu.umd.cs.findbugs.ba.AbstractFrameModelingVisitor#analyzeInstruction(org.apache.bcel.generic.Instruction)
083:             */
084:            @Override
085:            public void analyzeInstruction(Instruction ins)
086:                    throws DataflowAnalysisException {
087:                slotContainingNewNullValue = -1;
088:                super .analyzeInstruction(ins);
089:            }
090:
091:            /**
092:             * @return Returns the slotContainingNewNullValue; or -1 if no new null value
093:             *          was produced
094:             */
095:            public int getSlotContainingNewNullValue() {
096:                return slotContainingNewNullValue;
097:            }
098:
099:            @Override
100:            public IsNullValue getDefaultValue() {
101:                return IsNullValue.nonReportingNotNullValue();
102:            }
103:
104:            // Overrides of specific instruction visitor methods.
105:            // ACONST_NULL obviously produces a value that is DEFINITELY NULL.
106:            // LDC produces values that are NOT NULL.
107:            // NEW produces values that are NOT NULL.
108:
109:            // Note that all instructions that have an implicit null
110:            // check (field access, invoke, etc.) are handled in IsNullValueAnalysis,
111:            // because handling them relies on control flow (the existence of
112:            // an ETB and exception edge prior to the block containing the
113:            // instruction with the null check.)
114:
115:            // Note that we don't override IFNULL and IFNONNULL.
116:            // Those are handled in the analysis itself, because we need
117:            // to produce different values in each of the control successors.
118:
119:            private void produce(IsNullValue value) {
120:                IsNullValueFrame frame = getFrame();
121:                frame.pushValue(value);
122:                newValueOnTOS();
123:            }
124:
125:            private void produce2(IsNullValue value) {
126:                IsNullValueFrame frame = getFrame();
127:                frame.pushValue(value);
128:                frame.pushValue(value);
129:            }
130:
131:            /**
132:             * Handle method invocations.
133:             * Generally, we want to get rid of null information following a
134:             * call to a likely exception thrower or assertion.
135:             */
136:            private void handleInvoke(InvokeInstruction obj) {
137:                Type callType = obj.getLoadClassType(getCPG());
138:                Type returnType = obj.getReturnType(getCPG());
139:
140:                boolean stringMethodCall = callType.equals(Type.STRING)
141:                        && returnType.equals(Type.STRING);
142:
143:                // Determine if we are going to model the return value of this call.
144:                boolean modelCallReturnValue = MODEL_NONNULL_RETURN
145:                        && returnType instanceof  ReferenceType;
146:
147:                if (!modelCallReturnValue) {
148:                    // Normal case: Assume returned values are non-reporting non-null.
149:                    handleNormalInstruction(obj);
150:                } else {
151:                    // Special case: some special value is pushed on the stack for the return value
152:                    IsNullValue pushValue = null;
153:                    if (false && stringMethodCall) {
154:                        // String methods always return a non-null value
155:                        pushValue = IsNullValue.nonNullValue();
156:                    } else {
157:                        // Check to see if this method is in either database
158:                        XMethod calledMethod = XFactory.createXMethod(obj,
159:                                getCPG());
160:                        if (IsNullValueAnalysis.DEBUG)
161:                            System.out.println("Check " + calledMethod
162:                                    + " for null return...");
163:                        NullnessAnnotation annotation = AnalysisContext
164:                                .currentAnalysisContext()
165:                                .getNullnessAnnotationDatabase()
166:                                .getResolvedAnnotation(calledMethod, false);
167:                        Boolean alwaysNonNull = AnalysisContext
168:                                .currentAnalysisContext()
169:                                .getReturnValueNullnessPropertyDatabase()
170:                                .getProperty(calledMethod.getMethodDescriptor());
171:                        if (annotation == NullnessAnnotation.CHECK_FOR_NULL) {
172:                            if (IsNullValueAnalysis.DEBUG) {
173:                                System.out.println("Null value returned from "
174:                                        + calledMethod);
175:                            }
176:                            pushValue = IsNullValue
177:                                    .nullOnSimplePathValue()
178:                                    .markInformationAsComingFromReturnValueOfMethod(
179:                                            calledMethod);
180:                        } else if (annotation == NullnessAnnotation.NULLABLE) {
181:                            pushValue = IsNullValue.nonReportingNotNullValue();
182:                        } else if (annotation == NullnessAnnotation.NONNULL
183:                                || (alwaysNonNull != null && alwaysNonNull
184:                                        .booleanValue())) {
185:                            // Method is declared NOT to return null
186:                            if (IsNullValueAnalysis.DEBUG) {
187:                                System.out.println("NonNull value return from "
188:                                        + calledMethod);
189:                            }
190:                            pushValue = IsNullValue
191:                                    .nonNullValue()
192:                                    .markInformationAsComingFromReturnValueOfMethod(
193:                                            calledMethod);
194:
195:                        } else {
196:                            pushValue = IsNullValue.nonReportingNotNullValue();
197:                        }
198:                    }
199:
200:                    modelInstruction(obj, getNumWordsConsumed(obj),
201:                            getNumWordsProduced(obj), pushValue);
202:                    newValueOnTOS();
203:                }
204:
205:                if (!NO_ASSERT_HACK) {
206:                    if (assertionMethods.isAssertionCall(obj)) {
207:                        IsNullValueFrame frame = getFrame();
208:                        for (int i = 0; i < frame.getNumSlots(); ++i) {
209:                            IsNullValue value = frame.getValue(i);
210:                            if (value.isDefinitelyNull()
211:                                    || value.isNullOnSomePath()) {
212:                                frame.setValue(i, IsNullValue
213:                                        .nonReportingNotNullValue());
214:                            }
215:                        }
216:                        for (Map.Entry<ValueNumber, IsNullValue> e : frame
217:                                .getKnownValueMapEntrySet()) {
218:                            IsNullValue value = e.getValue();
219:                            if (value.isDefinitelyNull()
220:                                    || value.isNullOnSomePath())
221:                                e.setValue(IsNullValue
222:                                        .nonReportingNotNullValue());
223:
224:                        }
225:                    }
226:                }
227:            }
228:
229:            /**
230:             * Hook indicating that a new (possibly-null) value is on the
231:             * top of the stack.
232:             */
233:            private void newValueOnTOS() {
234:                IsNullValueFrame frame = getFrame();
235:                if (frame.getStackDepth() < 1) {
236:                    return;
237:                }
238:                int tosSlot = frame.getNumSlots() - 1;
239:                IsNullValue tos = frame.getValue(tosSlot);
240:                if (tos.isDefinitelyNull()) {
241:                    slotContainingNewNullValue = tosSlot;
242:                }
243:                if (trackValueNumbers) {
244:                    try {
245:                        ValueNumberFrame vnaFrameAfter = vnaDataflow
246:                                .getFactAfterLocation(getLocation());
247:                        if (vnaFrameAfter.isValid()) {
248:                            ValueNumber tosVN = vnaFrameAfter.getTopValue();
249:                            getFrame().setKnownValue(tosVN, tos);
250:                        }
251:                    } catch (DataflowAnalysisException e) {
252:                        AnalysisContext.logError("error", e);
253:                    }
254:                }
255:            }
256:
257:            @Override
258:            public void visitPUTFIELD(PUTFIELD obj) {
259:                if (getNumWordsConsumed(obj) != 2) {
260:                    super .visitPUTFIELD(obj);
261:                    return;
262:                }
263:
264:                IsNullValue nullValueStored = null;
265:                try {
266:                    nullValueStored = getFrame().getTopValue();
267:                } catch (DataflowAnalysisException e1) {
268:                    AnalysisContext.logError("Oops", e1);
269:                }
270:                super .visitPUTFIELD(obj);
271:                XField field = (XField) XFactory.createXField(obj, cpg);
272:                if (nullValueStored != null
273:                        && ValueNumberAnalysisFeatures.REDUNDANT_LOAD_ELIMINATION)
274:                    try {
275:                        ValueNumberFrame vnaFrameBefore = vnaDataflow
276:                                .getFactAtLocation(getLocation());
277:                        ValueNumber refValue = vnaFrameBefore.getStackValue(1);
278:                        AvailableLoad load = new AvailableLoad(refValue, field);
279:                        ValueNumberFrame vnaFrameAfter = vnaDataflow
280:                                .getFactAfterLocation(getLocation());
281:                        ValueNumber[] newValueNumbersForField = vnaFrameAfter
282:                                .getAvailableLoad(load);
283:                        if (newValueNumbersForField != null
284:                                && trackValueNumbers)
285:                            for (ValueNumber v : newValueNumbersForField)
286:                                getFrame().setKnownValue(v, nullValueStored);
287:                    } catch (DataflowAnalysisException e) {
288:                        AnalysisContext.logError("Oops", e);
289:                    }
290:            }
291:
292:            @Override
293:            public void visitGETFIELD(GETFIELD obj) {
294:                if (getNumWordsProduced(obj) != 1) {
295:                    super .visitGETFIELD(obj);
296:                    return;
297:                }
298:
299:                if (checkForKnownValue(obj)) {
300:                    return;
301:                }
302:
303:                XField field = XFactory.createXField(obj, cpg);
304:
305:                NullnessAnnotation annotation = AnalysisContext
306:                        .currentAnalysisContext()
307:                        .getNullnessAnnotationDatabase().getResolvedAnnotation(
308:                                field, false);
309:                if (annotation == NullnessAnnotation.NONNULL) {
310:                    modelNormalInstruction(obj, getNumWordsConsumed(obj), 0);
311:                    produce(IsNullValue.nonNullValue());
312:                } else if (annotation == NullnessAnnotation.CHECK_FOR_NULL) {
313:                    modelNormalInstruction(obj, getNumWordsConsumed(obj), 0);
314:                    produce(IsNullValue.nullOnSimplePathValue()
315:                            .markInformationAsComingFromFieldValue(field));
316:                } else {
317:
318:                    super .visitGETFIELD(obj);
319:                }
320:
321:            }
322:
323:            /* (non-Javadoc)
324:             * @see edu.umd.cs.findbugs.ba.AbstractFrameModelingVisitor#visitGETSTATIC(org.apache.bcel.generic.GETSTATIC)
325:             */
326:            @Override
327:            public void visitGETSTATIC(GETSTATIC obj) {
328:                if (getNumWordsProduced(obj) != 1) {
329:                    super .visitGETSTATIC(obj);
330:                    return;
331:                }
332:
333:                if (checkForKnownValue(obj)) {
334:                    return;
335:                }
336:                XField field = XFactory.createXField(obj, cpg);
337:                if (field.getClassName().equals("java.util.logging.Level")
338:                        && field.getName().equals("SEVERE")
339:                        || field.getClassName()
340:                                .equals("org.apache.log4j.Level")
341:                        && (field.getName().equals("ERROR") || field.getName()
342:                                .equals("FATAL")))
343:                    getFrame().toExceptionValues();
344:
345:                if (field.getName().startsWith("class$")) {
346:                    produce(IsNullValue.nonNullValue());
347:                    return;
348:                }
349:                NullnessAnnotation annotation = AnalysisContext
350:                        .currentAnalysisContext()
351:                        .getNullnessAnnotationDatabase().getResolvedAnnotation(
352:                                field, false);
353:                if (annotation == NullnessAnnotation.NONNULL) {
354:                    modelNormalInstruction(obj, getNumWordsConsumed(obj), 0);
355:                    produce(IsNullValue.nonNullValue());
356:                } else if (annotation == NullnessAnnotation.CHECK_FOR_NULL) {
357:                    modelNormalInstruction(obj, getNumWordsConsumed(obj), 0);
358:                    produce(IsNullValue.nullOnSimplePathValue()
359:                            .markInformationAsComingFromFieldValue(field));
360:                } else {
361:
362:                    super .visitGETSTATIC(obj);
363:                }
364:            }
365:
366:            /**
367:             * Check given Instruction to see if it produces a known value.
368:             * If so, model the instruction and return true.
369:             * Otherwise, do nothing and return false.
370:             * Should only be used for instructions that produce a single
371:             * value on the top of the stack.
372:             * 
373:             * @param obj the Instruction the instruction
374:             * @return true if the instruction produced a known value and was modeled,
375:             *          false otherwise
376:             */
377:            private boolean checkForKnownValue(Instruction obj) {
378:                if (trackValueNumbers) {
379:                    try {
380:                        // See if the value number loaded here is a known value
381:                        ValueNumberFrame vnaFrameAfter = vnaDataflow
382:                                .getFactAfterLocation(getLocation());
383:                        if (vnaFrameAfter.isValid()) {
384:                            ValueNumber tosVN = vnaFrameAfter.getTopValue();
385:                            IsNullValue knownValue = getFrame().getKnownValue(
386:                                    tosVN);
387:                            if (knownValue != null) {
388:                                //System.out.println("Produce known value!");
389:                                // The value produced by this instruction is known.
390:                                // Push the known value.
391:                                modelNormalInstruction(obj,
392:                                        getNumWordsConsumed(obj), 0);
393:                                produce(knownValue);
394:                                return true;
395:                            }
396:                        }
397:                    } catch (DataflowAnalysisException e) {
398:                        // Ignore...
399:                    }
400:                }
401:                return false;
402:            }
403:
404:            @Override
405:            public void visitACONST_NULL(ACONST_NULL obj) {
406:                produce(IsNullValue.nullValue());
407:            }
408:
409:            @Override
410:            public void visitNEW(NEW obj) {
411:                produce(IsNullValue.nonNullValue());
412:            }
413:
414:            @Override
415:            public void visitNEWARRAY(NEWARRAY obj) {
416:                modelNormalInstruction(obj, getNumWordsConsumed(obj), 0);
417:                produce(IsNullValue.nonNullValue());
418:            }
419:
420:            @Override
421:            public void visitANEWARRAY(ANEWARRAY obj) {
422:                modelNormalInstruction(obj, getNumWordsConsumed(obj), 0);
423:                produce(IsNullValue.nonNullValue());
424:            }
425:
426:            @Override
427:            public void visitMULTIANEWARRAY(MULTIANEWARRAY obj) {
428:                modelNormalInstruction(obj, getNumWordsConsumed(obj), 0);
429:                produce(IsNullValue.nonNullValue());
430:            }
431:
432:            @Override
433:            public void visitLDC(LDC obj) {
434:                produce(IsNullValue.nonNullValue());
435:            }
436:
437:            @Override
438:            public void visitLDC2_W(LDC2_W obj) {
439:                produce2(IsNullValue.nonNullValue());
440:            }
441:
442:            @Override
443:            public void visitCHECKCAST(CHECKCAST obj) {
444:                // Do nothing
445:            }
446:
447:            @Override
448:            public void visitINVOKESTATIC(INVOKESTATIC obj) {
449:                handleInvoke(obj);
450:            }
451:
452:            @Override
453:            public void visitINVOKESPECIAL(INVOKESPECIAL obj) {
454:                handleInvoke(obj);
455:            }
456:
457:            @Override
458:            public void visitINVOKEINTERFACE(INVOKEINTERFACE obj) {
459:                handleInvoke(obj);
460:            }
461:
462:            @Override
463:            public void visitINVOKEVIRTUAL(INVOKEVIRTUAL obj) {
464:                handleInvoke(obj);
465:            }
466:
467:        }
468:
469:        // 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.