Defective Java Code: Mistakes That Matter: William Pugh
Defective Java Code: Mistakes That Matter: William Pugh
William Pugh
Univ. of Maryland
Defective Java Code
Learning from mistakes
6
Mistakes in web services
7
Expensive mistakes (your results may vary)
8
Using reference equality rather than .equals
9
Using == to compare objects rather than .equals
10
Heisenbugs vs. deterministic bugs
11
Ignoring the return value of putIfAbsent
org.jgroups.protocols.pbcast.NAKACK
ConcurrentMap<Long,XmitTimeStat>
xmit_time_stat = ...;
.....
XmitTimeStat stat = xmit_time_stats.get(key);
if(stat == null) {
stat = new XmitTimeStat();
xmit_time_stats.putIfAbsent(key, stat);
}
stat.xmit_reqs_received.addAndGet(rcvd);
stat.xmit_rsps_sent.addAndGet(sent);
12
misusing putIfAbsent
org.jgroups.protocols.pbcast.NAKACK
XmitTimeStat stat=xmit_time_stats.get(key);
if(stat == null) {
stat=new XmitTimeStat();
XmitTimeStat stat2
= xmit_time_stats.putIfAbsent(key, stat);
if (stat2 != null)
stat = stat2;
}
stat.xmit_reqs_received.addAndGet(rcvd);
stat.xmit_rsps_sent.addAndGet(sent)
14
Some lessons
15
Mistakes Mistakes
That That
Matter Don’t
Unit Testing
System/Integration Testing
Deployment
Static Analysis
Static analysis earlier is better
18
Cross-site scripting
19
Cross site scripting
Trusted
WebSite Victim
html response contains script injected by
attacker, but treated by victim’s web
browser as though it came from trusted
web site
20
Security vulnerabilities
21
Returning references to internal mutable state
jdk1.7.0-b59
sun.security.x509.InvalidityDateExtension:
private Date date;
public Object get(String name) {
if (name.equalsIgnoreCase(DATE)) {
return date;
} else {...}
}
22
Vulnerability to malicious code
24
Incomparable equality
org.eclipse.jdt.internal.debug.eval.ast.engine.AstInstructionCompiler
25
Many variations, assisted by weak typing in APIs
26
Silent, nasty bugs
org.eclipse.pde.internal.build.BrandingIron
String target = root + '/' + ...;
File rootFolder
= getCanonicalFile(new File(initialRoot));
if (!rootFolder.equals(target)) {
rootFolder.delete();
...
}
28
Lost logger
void initLogger() {
Logger logger = Logger.getLogger("edu.umd.cs");
logger.addHandler(new FileHandler());
logger.setUseParentHandlers(false);
}
> Loggers are retained by weak references
• always allowed by spec, recent change to OpenJDK
implementation
> If GC happens immediately after the call to
initLogger, changes to logger will be lost
29
Lost Loggers at Google
30
Is this change compatible?
31
Listen to your bug stories
32
JBoss 5.1.0-GA
33
Improving software quality
34
Test, test, test...
35
Dead code
36
Code coverage from production
37
Cool idea
38
Leveraging class initialization logging
39
Using FindBugs to find mistakes
40
FindBugs 1.x
41
FindBugs 2.0
42
FindBugs 2.0
43
Bug ranking
44
FindBugs community review
45
More cloud integration
46
General availability Fall 2009
47
FindBugs community review
> Go to http://findbugs.sourceforge.net/review
> Launch FindBugs GUI via webstart
> Review issues in
• jdk1.7.0
• Glassfish-v3
• Eclipse 3.5
> Everyone welcome
• very much a beta
• no integration with bug tracking systems yet
48
Demo
49
William Pugh
[email protected]
http://findbugs.sourceforge.net/