<?xml version='1.0' encoding='UTF-8'?><?xml-stylesheet href="http://www.blogger.com/styles/atom.css" type="text/css"?><feed xmlns='http://www.w3.org/2005/Atom' xmlns:openSearch='http://a9.com/-/spec/opensearchrss/1.0/' xmlns:georss='http://www.georss.org/georss'><id>tag:blogger.com,1999:blog-6715087</id><updated>2009-12-16T13:28:27.779-08:00</updated><title type='text'>Dadidadida</title><subtitle type='html'>by Hanson Char</subtitle><link rel='http://schemas.google.com/g/2005#feed' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/posts/default'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default?orderby=updated'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/'/><link rel='hub' href='http://pubsubhubbub.appspot.com/'/><link rel='next' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default?start-index=26&amp;max-results=25&amp;orderby=updated'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email></author><generator version='7.00' uri='http://www.blogger.com'>Blogger</generator><openSearch:totalResults>118</openSearch:totalResults><openSearch:startIndex>1</openSearch:startIndex><openSearch:itemsPerPage>25</openSearch:itemsPerPage><entry><id>tag:blogger.com,1999:blog-6715087.post-5516135818010480825</id><published>2009-11-03T09:40:00.000-08:00</published><updated>2009-11-03T09:45:44.199-08:00</updated><title type='text'>SHA-1 and MD5: Mac vs Java</title><content type='html'>&lt;pre&gt;echo -n "" | openssl dgst -sha1&lt;br /&gt;=&gt; da39a3ee5e6b4b0d3255bfef95601890afd80709&lt;br /&gt;&lt;br /&gt;echo -n "" | md5&lt;br /&gt;=&gt; d41d8cd98f00b204e9800998ecf8427e&lt;br /&gt;&lt;br /&gt;public class FooCrypt {&lt;br /&gt;    public static void main(String[] args) throws Exception {&lt;br /&gt;        MessageDigest sha1 = MessageDigest.getInstance("SHA-1");&lt;br /&gt;        System.out.println("sha-1: " + bytesToHex(sha1.digest("".getBytes("UTF-8"))));&lt;br /&gt;        MessageDigest md5 = MessageDigest.getInstance("MD5");&lt;br /&gt;        System.out.println("md5: " + bytesToHex(md5.digest("".getBytes("UTF-8"))));&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    public static String bytesToHex(byte[] bs) {&lt;br /&gt;        StringBuilder ret = new StringBuilder(bs.length);&lt;br /&gt;        for (int i = 0; i &lt; bs.length; i++) {&lt;br /&gt;            String hex = Integer.toHexString(0x0100 + (bs[i] &amp; 0x00FF)).substring(1);&lt;br /&gt;            ret.append((hex.length() &lt; 2 ? "0" : "")).append(hex);&lt;br /&gt;        }&lt;br /&gt;        return ret.toString();&lt;br /&gt;    }&lt;br /&gt;}&lt;br /&gt;&lt;br /&gt;=&gt; &lt;br /&gt;sha-1: da39a3ee5e6b4b0d3255bfef95601890afd80709&lt;br /&gt;md5: d41d8cd98f00b204e9800998ecf8427e&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-5516135818010480825?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/5516135818010480825/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=5516135818010480825' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5516135818010480825'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5516135818010480825'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2009/11/sha-1-and-md5-mac-vs-java.html' title='SHA-1 and MD5: Mac vs Java'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-8866521705036608591</id><published>2009-10-25T16:56:00.000-07:00</published><updated>2009-11-01T01:00:03.668-08:00</updated><title type='text'>Experimenting with Oracle DBMS_LOCK</title><content type='html'>First, grant privilege to play with it.  For example,&lt;pre&gt;&lt;blockquote&gt;Login as user SYS with SYSDBA role, then&lt;br /&gt;&lt;br /&gt;  grant all on dbms_lock to public;&lt;/blockquote&gt;&lt;/pre&gt;How to try it out in SQL Developer ?&lt;pre&gt;&lt;blockquote&gt;set serveroutput on;&lt;br /&gt;&lt;br /&gt;declare&lt;br /&gt;  v_result integer;&lt;br /&gt;begin&lt;br /&gt;  v_result := DBMS_LOCK.REQUEST(123, 6, 0, true);&lt;br /&gt;  &lt;br /&gt;  dbms_output.put_line(&lt;br /&gt;           case &lt;br /&gt;              when v_result=0 then 'Success'&lt;br /&gt;              when v_result=1 then 'Timeout'&lt;br /&gt;              when v_result=2 then 'Deadlock'&lt;br /&gt;              when v_result=3 then 'Parameter Error'&lt;br /&gt;              when v_result=4 then 'Already owned'&lt;br /&gt;              when v_result=5 then 'Illegal Lock Handle'&lt;br /&gt;           end);&lt;br /&gt;end;&lt;br /&gt;&lt;/blockquote&gt;&lt;/pre&gt;How to do it in JDBC ?&lt;br /&gt;&lt;pre&gt;&lt;blockquote&gt;  Connection conn = ...&lt;br /&gt;  CallableStatement stmt = conn.prepareCall("{call ? := DBMS_LOCK.REQUEST(?, 6, 0, true)}");&lt;br /&gt;  stmt.registerOutParameter(1, Types.INTEGER);&lt;br /&gt;  stmt.setBigDecimal(2, new BigDecimal(123));&lt;br /&gt;  stmt.execute();&lt;br /&gt;  int result = stmt.getInt(1);&lt;br /&gt;  System.out.println("result: " + result);&lt;/blockquote&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-8866521705036608591?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/8866521705036608591/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=8866521705036608591' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/8866521705036608591'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/8866521705036608591'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2009/10/oracle-dbmslock-experiments.html' title='Experimenting with Oracle DBMS_LOCK'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-8293954121015940159</id><published>2009-10-26T18:15:00.000-07:00</published><updated>2009-10-26T18:16:58.478-07:00</updated><title type='text'>What comes next ?</title><content type='html'>3&lt;br /&gt;1 3&lt;br /&gt;1 1 1 3&lt;br /&gt;3 1 1 3&lt;br /&gt;1 3 2 1 1 3&lt;br /&gt;1 1 1 3 1 2 2 1 1 3&lt;br /&gt;3 1 1 3 1 1 2 2 2 1 1 3&lt;br /&gt;1 3 2 1 1 3 2 1 3 2 2 1 1 3&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-8293954121015940159?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/8293954121015940159/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=8293954121015940159' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/8293954121015940159'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/8293954121015940159'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2009/10/what-comes-next.html' title='What comes next ?'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-867488047772701207</id><published>2009-09-07T18:10:00.000-07:00</published><updated>2009-09-07T18:38:09.916-07:00</updated><title type='text'>S3/SimpleDB Limitations</title><content type='html'>&lt;a href="http://docs.amazonwebservices.com/AmazonS3/latest/BucketRestrictions.html"&gt;&lt;br /&gt;S3 Limits&lt;/a&gt; - max 100 buckets per account, unlimited number of objects per bucket with &lt;a href="http://docs.amazonwebservices.com/AmazonS3/latest/UsingObjects.html"&gt;object size &lt; 5GB&lt;/a&gt;&lt;br /&gt;&lt;br /&gt;&lt;a href="http://docs.amazonwebservices.com/AmazonSimpleDB/latest/DeveloperGuide/SDBLimits.html"&gt;SimpleDB Limits&lt;/a&gt; - max 10 GB per domain, max 100 domains per account, max 1KB attribute value, max 256 attributes per item&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-867488047772701207?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/867488047772701207/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=867488047772701207' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/867488047772701207'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/867488047772701207'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2009/09/aws-limitations.html' title='S3/SimpleDB Limitations'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-2725262524368321045</id><published>2007-06-18T15:31:00.000-07:00</published><updated>2009-09-01T12:39:35.928-07:00</updated><title type='text'>OpenSsl/Keytool Cheat Sheet</title><content type='html'>&lt;pre&gt;# Convert an RSA public key from PEM to DER&lt;br /&gt;openssl rsa -inform PEM -in test-public-key.pem -outform DER -out test-public-key.der -pubin&lt;br /&gt;&lt;br /&gt;# Convert a X509 certificate from PEM to DER&lt;br /&gt;openssl x509 -in test-x509-cert.pem -inform PEM -out test-x509-cert.der -outform DER&lt;br /&gt;&lt;br /&gt;# Print a X509 certificate&lt;br /&gt;openssl x509 -text -in test-public-cert.pem&lt;br /&gt;&lt;br /&gt;# Import a certificate to JKS&lt;br /&gt;jdk1.6.0/bin/keytool -storepass changeit -keystore truststore.jks -importcert -alias mycert -file mycert.der -trustcacerts&lt;br /&gt;&lt;br /&gt;# &lt;a href="http://www.agentbob.info/agentbob/79.html"&gt;http://www.agentbob.info/agentbob/79.html&lt;/a&gt;&lt;br /&gt;# Read the javadoc in ImportKey.java for details of converting it to a keystore&lt;br /&gt;&lt;br /&gt;# Convert a private key from PEM to DER&lt;br /&gt;openssl pkcs8 -topk8 -nocrypt -in private-key.pem -out private-key.der -outform der&lt;br /&gt;&lt;br /&gt;# Convert cert from PEM to DER&lt;br /&gt;openssl x509 -in cert.pem -out cert.der -outform der&lt;br /&gt;&lt;br /&gt;# Convert private key and cert to keystore&lt;br /&gt;java -cp . ImportKey private-key.der cert.der&lt;br /&gt;&lt;br /&gt;# Change the storepass&lt;br /&gt;keytool -keystore keystore.jks -storepass importkey -storepasswd -new changeit&lt;br /&gt;&lt;br /&gt;# Change the alias&lt;br /&gt;keytool -keystore keystore.jks -storepass changeit -changealias -alias importkey -keypass importkey -destalias myhost&lt;br /&gt;&lt;br /&gt;# Change the keypass&lt;br /&gt;keytool -keystore keystore.jks -storepass changeit -alias myhost -keypasswd -keypass importkey -new changeit&lt;br /&gt;&lt;br /&gt;# List the keystore&lt;br /&gt;keytool -keystore keystore.jks -storepass changeit -list -v&lt;br /&gt;&lt;br /&gt;# How to generate a self-signed key pairs using keytool ?&lt;br /&gt;keytool -genkeypair -dname "cn=myname,ou=myunit,o=myorg,c=AU" -alias myalias -keypass changeit -keystore ./my-keystore.jks&lt;br /&gt;-keypass changeit -storepass changeit -validity 9999 -v&lt;br /&gt;&lt;br /&gt;### Extracting the certificate (public key) ###&lt;br /&gt;&lt;br /&gt;# Export the X509 certificate&lt;br /&gt;keytool -export -alias myalias -keystore my-keystore.jks -storepass changeit -file mycert.der&lt;br /&gt;&lt;br /&gt;# Display it&lt;br /&gt;openssl x509 -noout -text -in mycert.der -inform der&lt;br /&gt;&lt;br /&gt;# Convert to PEM&lt;br /&gt;openssl x509 -out mycert.pem -outform pem -in mycert.der -inform der&lt;br /&gt;&lt;br /&gt;### Extracting the private key ###&lt;br /&gt;&lt;br /&gt;#Download, compile &amp; run &lt;a href="http://mark.foster.cc/pub/java/ExportPriv.java"&gt;ExportPriv&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;# Export private key into pcks8 format&lt;br /&gt;javac ExportPriv.java&lt;br /&gt;java ExportPriv my-keystore.jks myalias changeit &amp;gt; my-key.pkcs8&lt;br /&gt;&lt;br /&gt;# Combine public and private key into pkcs12 format&lt;br /&gt;openssl pkcs12 -export -out my-key.p12 -inkey my-key.pkcs8 -in my-cert.pem&lt;br /&gt;&lt;br /&gt;# Convert pkc12 to PEM so it can be displayed&lt;br /&gt;openssl pkcs12 -in pkcs-12-certificate(-and-key-file) -out pem-certificate(-and-key-file)&lt;br /&gt;&lt;/pre&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-2725262524368321045?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/2725262524368321045/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=2725262524368321045' title='7 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/2725262524368321045'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/2725262524368321045'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2007/06/opensslkeytool-cheat-sheet.html' title='OpenSsl/Keytool Cheat Sheet'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>7</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-4905154343612005849</id><published>2009-04-25T10:54:00.000-07:00</published><updated>2009-05-10T10:14:33.056-07:00</updated><title type='text'>Covariant Enum Idiom</title><content type='html'>Say we want to have a Java Enum that can return different types from the same method by different constants, how could we go about writing it ?  How about something like:&lt;blockquote&gt;&lt;pre&gt;/**&lt;br /&gt; * An enum that can polymorphically return different types of object.&lt;br /&gt; */&lt;br /&gt;public enum CovariantEnum {&lt;br /&gt;    A { &lt;br /&gt;        @Override public String getValue() { return "CovariantEnum.A"; } &lt;br /&gt;    },&lt;br /&gt;    B {&lt;br /&gt;        @Override public Integer getValue() { return 1; }&lt;br /&gt;    },&lt;br /&gt;    // etc.&lt;br /&gt;    ;&lt;br /&gt;    public abstract &amp;lt;T&gt; T getValue();&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;This would actually compile, except there are two problems.  First, there are compilation warnings about "return type requires unchecked conversion".  Second, it actually doesn't quite work as expected.  Client code such as:&lt;blockquote&gt;&lt;pre&gt;// This doesn't work :(&lt;br /&gt;String stringValue = CovariantEnum.A.getValue();&lt;/pre&gt;&lt;/blockquote&gt;would result in a type mismatch compilation error.  Explicit casting the returned value to the target type, such as String in the above example, would work, but that defeats the purpose of building CovariantEnum in the first place.&lt;br /&gt;&lt;br /&gt;So how can we get around these limitations ?&lt;br /&gt;&lt;br /&gt;Well, first, Java disallows enum declaration to have type parameters.  In other words, it is a syntax error to write:&lt;blockquote&gt;&lt;pre&gt;public enum CovariantEnum&amp;lt;T&gt; {&lt;br /&gt;...&lt;/pre&gt;&lt;/blockquote&gt;But what if we emulate a enum with an abstract class ?  This may lead to something like:&lt;blockquote&gt;&lt;pre&gt;/**&lt;br /&gt; * Basically a "CovariantEnum" that actually works and does not cause any compilation warnings.&lt;br /&gt; */&lt;br /&gt;public abstract class TypeSafeCovariantEnum&amp;lt;T&gt; {&lt;br /&gt;    public static final TypeSafeCovariantEnum&amp;lt;String&gt; A = new TypeSafeCovariantEnum&amp;lt;String&gt;() { &lt;br /&gt;        @Override public String getValue() { return "TypeSafeCovariantEnum.A"; } &lt;br /&gt;    };&lt;br /&gt;    public static final TypeSafeCovariantEnum&amp;lt;Integer&gt; B = new TypeSafeCovariantEnum&amp;lt;Integer&gt;() { &lt;br /&gt;        @Override public Integer getValue() { return 1; }&lt;br /&gt;    };&lt;br /&gt;    &lt;br /&gt;    private TypeSafeCovariantEnum() {}&lt;br /&gt;    public abstract T getValue();&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;Now compilation has zero warnings, and a client can enjoy using the "literal instances" in TypeSafeCovariantEnum as if it's a covariant enum without any need for explicit casting:&lt;blockquote&gt;&lt;pre&gt;// This works!&lt;br /&gt;String stringValue = TypeSafeCovariantEnum.A.getValue();&lt;br /&gt;Integer integerValue = TypeSafeCovariantEnum.B.getValue();&lt;/pre&gt;&lt;/blockquote&gt;Of course this is not an actual enum, and it involves a little complexity inside; but it provides 100% type safety, and simplicity to the clients outside :-)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-4905154343612005849?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/4905154343612005849/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=4905154343612005849' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4905154343612005849'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4905154343612005849'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2009/04/covariant-enum-pattern.html' title='Covariant Enum Idiom'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-3851988195511373606</id><published>2007-05-21T00:39:00.001-07:00</published><updated>2009-01-07T13:56:16.518-08:00</updated><title type='text'>Heap Dump in Java 6</title><content type='html'>Just experimenting with the use of jmap and jhat in Java 6.  The Object Query Language in jhat that allows the use of javascript closure seems pretty powerful, though also pretty slow.&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Practices&lt;/span&gt;&lt;br /&gt;# Find out the jvm pid&lt;br /&gt;jps &lt;br /&gt;# Trigger heap dump&lt;br /&gt;jmap -dump:format=b,file=/tmp/java_app-heap.bin &amp;lt;pid&gt;&lt;br /&gt;&lt;br /&gt;# Analyzing the heap dump&lt;br /&gt;jhat -J-Xmx326m /tmp/java_app-heap.bin&lt;br /&gt;&lt;br /&gt;http://localhost:7000/showInstanceCounts/&lt;br /&gt;http://localhost:7000/oql&lt;blockquote&gt;&lt;pre&gt;#Find out the total size of MyClass instances&lt;br /&gt;select sum(map(heap.objects('foo.bar.MyClass'), 'sizeof(it)'))&lt;br /&gt;&lt;br /&gt;# List out all class names matching "foo.bar"&lt;br /&gt;select filter(heap.classes(), "/foo.bar/(it.name)")&lt;br /&gt;&lt;br /&gt;# Ditto&lt;br /&gt;select map(filter(heap.classes(), "/foo.bar/(it.name)"),&lt;br /&gt;    function(c) {&lt;br /&gt;      return "&amp;lt;br&gt;"+ c.name;&lt;br /&gt;    })&lt;br /&gt;&lt;br /&gt;# List classes that match "foo.bar" with instances &gt; 0&lt;br /&gt;select map(filter(heap.classes(), "/foo.bar/(it.name)"),&lt;br /&gt;    function(c) {&lt;br /&gt;      var len = length(heap.objects(c));&lt;br /&gt;      if (len == 0) return "";&lt;br /&gt;      return "&amp;lt;br&gt;" + c.name + ", instances:" + len;&lt;br /&gt;    })&lt;br /&gt;&lt;br /&gt;# List classes that match "foo.bar" with instance sizes &gt; 0&lt;br /&gt;select map(filter(heap.classes(), "/foo.bar/(it.name)"),&lt;br /&gt;    function(c) {&lt;br /&gt;      var totalsize = sum(map(heap.objects(c), &lt;br /&gt;          function(o) {&lt;br /&gt;              return sizeof(o);&lt;br /&gt;          }&lt;br /&gt;      ));&lt;br /&gt;      if (totalsize == 0) return "";&lt;br /&gt;      return "&amp;lt;br&gt;" + c.name + ", size:" + totalsize;&lt;br /&gt;    })&lt;/pre&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;More info&lt;/span&gt;&lt;br /&gt;&lt;a href="http://javatools.wordpress.com/2007/03/29/howto-find-java-memory-leaks/"&gt;How to find java memory leaks&lt;/a&gt;&lt;br /&gt;&lt;a href="http://java.sun.com/javase/6/webnotes/trouble/TSG-VM/html/tools.html"&gt;Troubleshooting Guide for Java SE 6 with HotSpot VM&lt;/a&gt;&lt;br /&gt;&lt;a href="http://blogs.sun.com/alanb/entry/heapdumponoutofmemoryerror_option_in_5_0u7"&gt;HeapDumpOnOutOfMemoryError option in 5.0u7 and 1.4.2_12&lt;/a&gt;&lt;br /&gt;&lt;a href="http://blogs.sun.com/sundararajan/entry/permanent_generation_analysis_with_oql"&gt;Permanent generation analysis with OQL&lt;/a&gt;&lt;br /&gt;&lt;a href="http://blogs.sun.com/sundararajan/entry/what_s_in_my_java"&gt;What's in my Java heap?&lt;/a&gt;&lt;br /&gt;&lt;a href="http://blogs.sun.com/sundararajan/entry/querying_java_heap_with_oql"&gt;Querying Java heap with OQL&lt;/a&gt;&lt;br /&gt;&lt;a href="http://blogs.sun.com/edwardchou/entry/javaone_bof_on_memory_leaks"&gt;JavaOne 2007 BOF on Memory Leaks&lt;/a&gt;&lt;br /&gt;&lt;a href="http://blogs.sun.com/fkieviet/entry/javaone_2007"&gt;BOF9982: The java.lang.OutOfMemoryError: PermGen Space error demystified&lt;/a&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-3851988195511373606?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/3851988195511373606/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=3851988195511373606' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/3851988195511373606'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/3851988195511373606'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2007/05/heap-dump-in-java-6.html' title='Heap Dump in Java 6'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-7946110647380470533</id><published>2008-11-30T00:24:00.000-08:00</published><updated>2008-12-28T21:04:57.117-08:00</updated><title type='text'>Local vs Any address in Cajo</title><content type='html'>Looking into the &lt;a href="https://cajo.dev.java.net/"&gt;cajo&lt;/a&gt; source code, I see the default server side host address used by cajo is the local host address.  For example,&lt;blockquote&gt;&lt;pre&gt;host = InetAddress.getLocalHost().getHostAddress();&lt;/pre&gt;&lt;/blockquote&gt;This seems to work in most cases/platforms, except it breaks with the new Mac that I have.  How does it break ?  Well the server side binding works with the default (local) address, but the client would fail to connect to 127.0.0.1 or localhost.  To make the client connect, I needed to figure out the specific local address (like 192.168.0.3) used for the server side binding, and explicitly specify that for the client.&lt;br /&gt;&lt;br /&gt;When I tried to see if this was also the case outside cajo using the plain old ServerSocket(int), surprisingly it worked regardless of whether I specified locahost, 127.0.0.1, or 192.168.0.3.&lt;br /&gt;&lt;br /&gt;Digging more into the JDK source code, ServerSocket uses an "any address" rather than a "local address" as the default:&lt;blockquote&gt;&lt;pre&gt;InetAddress.anyLocalAddress();&lt;/pre&gt;&lt;/blockquote&gt;Sadly, this static method is package private.&lt;br /&gt;&lt;br /&gt;Anyhow, since the "any address" seems to work more so than the "local address", it would be nice if cajo can change the default server side address to the "any address", which would make cajo "just work" across more platforms.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-7946110647380470533?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/7946110647380470533/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=7946110647380470533' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/7946110647380470533'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/7946110647380470533'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/11/local-vs-any-address-in-cajo.html' title='Local vs Any address in Cajo'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-111975760626030011</id><published>2005-06-25T20:40:00.000-07:00</published><updated>2008-11-26T22:56:13.803-08:00</updated><title type='text'>Why use beanlib with Hibernate ?</title><content type='html'>&lt;font color="red"&gt;(This post is about Beanlib 2.x.  Please go to the &lt;a href="http://beanlib.sourceforge.net/" target="_blank"&gt;JavaBean Library&lt;/a&gt; home page for the latest and greatest.)&lt;/font&gt;&lt;br /&gt;&lt;br /&gt;Put simply, in cloning a Hibernate entity bean, we want to specify how deep we want to go in the object graph. Is it a 100% deep clone, a skin deep shallow clone, or some other combinations ? How about beans that involve a one-to-many collection ? The answer to this question has a significant impact on both the performance and memory footprint of the cloning process.&lt;br /&gt;&lt;br /&gt;The &lt;a href="http://sourceforge.net/projects/beanlib" target="_blank"&gt;JavaBean Library&lt;/a&gt; provides the following options&lt;ol&gt;&lt;li&gt;100% deep clone which will result in eagerly fetching all related entites and populating the values into pure POJO's which therefore will get rid of all CGLIB enhanced instances;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Shallow clone which will result in cloning the top level bean and the immediately contained member fields of Java primitive types, String, Date, etc., but will exclude instances of Collection and application specific types. The excluded member fields will be set to null;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Partial deep clone that extends only to a specified set of classes and a specified set of "collection properties". A collection property can be specified via a class named &lt;span style="font-weight: bold;"&gt;CollectionPropertyName&lt;/span&gt;. This allows an arbitrary portion of the object graph to be deeply cloned;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Provide your own customized "Vetoer" by implementing the &lt;span style="font-weight: bold;"&gt;BeanPopulatable&lt;/span&gt; interface to control the population decision of each bean property;&lt;/li&gt;&lt;br /&gt;&lt;li&gt;Provide your own customized &lt;span style="font-weight: bold;"&gt;BeanPopulatable&lt;/span&gt; and/or &lt;span style="font-weight: bold;"&gt;DetailedBeanPopulatable&lt;/span&gt; to completely override the population decision of each bean property.&lt;/li&gt;&lt;br /&gt;&lt;li&gt;A new enhancement can be found &lt;a href="http://hansonchar.blogspot.com/2005/08/beanlib-241.html"&gt;here&lt;/a&gt;.&lt;/li&gt;&lt;/ol&gt;The class used for the above cloning is named &lt;span style="font-weight: bold;"&gt;HibernateBeanReplicator&lt;/span&gt;. There exists one for Hibernate 2.x and one for Hibernate 3.x.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-111975760626030011?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/111975760626030011/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=111975760626030011' title='33 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/111975760626030011'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/111975760626030011'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2005/06/why-use-beanlib-with-hibernate.html' title='Why use &lt;a href=&quot;http://sourceforge.net/projects/beanlib&quot; target=&quot;_blank&quot;&gt;beanlib&lt;/a&gt; with Hibernate ?'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>33</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-447773896266447223</id><published>2008-11-22T07:51:00.000-08:00</published><updated>2008-11-22T09:18:51.950-08:00</updated><title type='text'>Warming up a JVM</title><content type='html'>If you knew the actual set of classes that will be lazily loaded into the JVM for execution, wouldn't it be nice if these classes can be eagerly loaded into the JVM upon start-up ?  This particularly matters if you are writing web services, where the latency of the first few requests will be significantly impacted.&lt;br /&gt;&lt;br /&gt;Pre-loading classes is easy.  But how can we find out the precise set of classes to be preloaded ?  It turns out there exists a very nice JVM option:&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;-verbose:class&lt;/pre&gt;&lt;/blockquote&gt;Also found an interesting technical report: &lt;a href="http://ecommons.library.cornell.edu/handle/1813/5832"&gt;Eager Class Initialization For Java&lt;/a&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-447773896266447223?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/447773896266447223/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=447773896266447223' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/447773896266447223'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/447773896266447223'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/11/jvm-warm-up.html' title='Warming up a JVM'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-2884032726316838090</id><published>2007-12-28T17:58:00.000-08:00</published><updated>2008-11-13T23:37:16.666-08:00</updated><title type='text'>File Distribution and Replication via JGroups</title><content type='html'>Here is how I used JGroups (2.6.1) to distribute and replicate files retrieved from a feed, so there is no single point of failure:&lt;blockquote&gt;&lt;a href="http://www.nabble.com/Re%3A-Streaming-Message-Transfer---p14510203.html"&gt;http://www.nabble.com/Re%3A-Streaming-Message-Transfer---p14510203.html&lt;/a&gt;&lt;/blockquote&gt;Here is a reply from Bela Ban basically confirming that the scheme works (via configuring a TCP stack):&lt;blockquote&gt;&lt;a href="http://www.nabble.com/Re%3A-Streaming-Message-Transfer---p14512866.html"&gt;http://www.nabble.com/Re%3A-Streaming-Message-Transfer---p14512866.html&lt;/a&gt;&lt;/blockquote&gt;The whole thread:&lt;blockquote&gt;&lt;a href="http://www.nabble.com/Streaming-Message-Transfer---td14476343.html"&gt;http://www.nabble.com/Streaming-Message-Transfer---td14476343.html&lt;/a&gt;&lt;/blockquote&gt;JGroups rocks!&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style:italic;"&gt;Update on 13Nov08:&lt;/span&gt;  Or does it ?  After using JGroups for about a year now, it seems JGroups can be quite unreliable when the number of nodes in a cluster grow beyond half a dozen of nodes, especially if they span across a WAN.  Or maybe it's just me ?&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-2884032726316838090?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/2884032726316838090/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=2884032726316838090' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/2884032726316838090'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/2884032726316838090'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2007/12/file-distribution-and-replication-via.html' title='File Distribution and Replication via JGroups'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-2375866515027723928</id><published>2008-11-11T11:43:00.000-08:00</published><updated>2008-11-12T08:17:54.536-08:00</updated><title type='text'>A little Java constructor pattern</title><content type='html'>Say we have a class Item:&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;public class Item {&lt;br /&gt;    final String name;&lt;br /&gt;    final float val;&lt;br /&gt;    final int size;&lt;br /&gt;    &lt;br /&gt;    public Item(String name, int size, float val) {&lt;br /&gt;        this.name = name;&lt;br /&gt;        this.val = val;&lt;br /&gt;        this.size = size;&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;and we'd like to initialize an Item array with some values:&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;Item[] items = {&lt;br /&gt;    new Item("A", 3, 4),&lt;br /&gt;    new Item("B", 4, 5),&lt;br /&gt;    ...&lt;br /&gt;};&lt;/pre&gt;&lt;/blockquote&gt;Wouldn't it be nice if we can simplify it to:&lt;blockquote&gt;&lt;pre&gt;Item[] items = {&lt;br /&gt;    Item("A", 3, 4),&lt;br /&gt;    Item("B", 4, 5),&lt;br /&gt;    ...&lt;br /&gt;};&lt;/pre&gt;&lt;/blockquote&gt;?  &lt;br /&gt;&lt;br /&gt;Couldn't this be easily done by defining a static factory method with the same name as Item, and then use it via static import ?&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;public class Item {&lt;br /&gt;    // ... same as above&lt;br /&gt;&lt;br /&gt;    // A static factory method for the syntactic sugar&lt;br /&gt;    public static Item Item(String name, int size, float val) {&lt;br /&gt;        return new Item(name, size, val);&lt;br /&gt;    }&lt;br /&gt;}&lt;br /&gt;&lt;/pre&gt;&lt;/blockquote&gt;Usage:&lt;blockquote&gt;&lt;pre&gt;import static Item.Item;&lt;br /&gt;...&lt;br /&gt;Item[] items = {&lt;br /&gt;    Item("A", 3, 4),&lt;br /&gt;    Item("B", 4, 5),&lt;br /&gt;    ...&lt;br /&gt;};&lt;/pre&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-2375866515027723928?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/2375866515027723928/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=2375866515027723928' title='3 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/2375866515027723928'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/2375866515027723928'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/11/little-java-constructor-pattern.html' title='A little Java constructor pattern'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>3</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-5518153776399001494</id><published>2008-09-23T16:14:00.000-07:00</published><updated>2008-09-23T16:22:44.992-07:00</updated><title type='text'>Beanlib on BeanUtils wiki</title><content type='html'>It made my day when I proposed to use &lt;a href="http://beanlib.sourceforge.net/"&gt;Beanlib&lt;/a&gt; to solve a &lt;a href="http://www.nabble.com/PropertyUtils.copyProperties()-and-inherited-classes-td19622863.html"&gt;problem&lt;/a&gt; which the Jakarta Commons &lt;a href="http://commons.apache.org/beanutils/"&gt;BeanUtils&lt;/a&gt; was not well suited, Beanlib ended up being included in the &lt;a href="http://wiki.apache.org/commons/BeanUtils"&gt;BeanUtils wiki&lt;/a&gt; as a related project :)&lt;br /&gt;&lt;br /&gt;Thanks to Niall Pemberton for being open minded.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-5518153776399001494?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/5518153776399001494/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=5518153776399001494' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5518153776399001494'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5518153776399001494'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/09/beanlib-on-beanutils-wiki.html' title='Beanlib on BeanUtils wiki'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-4888878132253509738</id><published>2008-09-22T12:35:00.000-07:00</published><updated>2008-09-22T13:53:33.174-07:00</updated><title type='text'>No more infinitely blocking socket ?</title><content type='html'>One common problem Java programmer faces is the direct or indirect use of socket that could block forever.  If a socket connect or read operation blocks with an infinite timeout, there is basically nothing that can interrupt the blocking thread besides closing the socket.  Not Thread.interrupt(), nor even Thread.stop() would help.  Gaining access to the underlying socket could, however, be difficult, considering the socket could be buried deep down inside some third party library, such as a JDBC driver.&lt;br /&gt;&lt;br /&gt;Attending the &lt;a href="http://www.nofluffjuststuff.com/conference/seattle/2008/09/index.html"&gt;NFJS&lt;/a&gt; session, &lt;a href="http://www.nofluffjuststuff.com/speaker_topic_view.jsp?topicId=795"&gt;Busy Java Developer's Guide to JDK Hacking&lt;/a&gt; by &lt;a href="http://www.nofluffjuststuff.com/conference/speaker/ted_neward.html"&gt;Ted Neward&lt;/a&gt; yesterday, a solution came to my mind when Ted demonstrated how easy it was to slip in my own classes ahead of the JDK's.  Why not simply extend the existing JDK socket implementation with an additional system property to limit or default the socket timeout to some sensible values ?  See an example implementation below.  To make this work, simply &lt;ol&gt;&lt;li&gt;Set up a custom socket factory:&lt;blockquote&gt;&lt;pre&gt;Socket.setSocketImplFactory(new SocketImplFactory() {&lt;br /&gt;    @Override&lt;br /&gt;    public SocketImpl createSocketImpl() { return new NicerSocksSocketImpl(); }&lt;br /&gt;});&lt;/pre&gt;&lt;/blockquote&gt;&lt;li&gt;Slip in the implementation class and configure the socket timeout when starting up the JVM:&lt;blockquote&gt;&lt;pre&gt;java -Xbootclasspath/p:"/path/to/custom/jdk/classes" -DSO_TIMEOUT=1000 ...&lt;/pre&gt;&lt;/blockquote&gt;&lt;/ol&gt;Now if a socket timeout is not specified by the individual application or library, the blocking operation would be limited to a maximum of 1,000ms before throwing up.&lt;br /&gt;&lt;br /&gt;No more socket black hole sucking up resources:)&lt;blockquote&gt;&lt;pre&gt;package java.net;&lt;br /&gt;import java.io.IOException;&lt;br /&gt;&lt;br /&gt;public class NicerSocksSocketImpl extends SocksSocketImpl {&lt;br /&gt;    private final int defaultSoTimeout; &lt;br /&gt;&lt;br /&gt;    public NicerSocksSocketImpl() { this.defaultSoTimeout = defaultSoTimeout(); }&lt;br /&gt;&lt;br /&gt;    public NicerSocksSocketImpl(String server, int port) {&lt;br /&gt;        super(server, port);&lt;br /&gt;        this.defaultSoTimeout = defaultSoTimeout();&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    public NicerSocksSocketImpl(Proxy proxy) {&lt;br /&gt;        super(proxy);&lt;br /&gt;        this.defaultSoTimeout = defaultSoTimeout();&lt;br /&gt;    }&lt;br /&gt;    &lt;br /&gt;    private int defaultSoTimeout() {&lt;br /&gt;        String defaultSoTimeoutStr = System.getProperty("SO_TIMEOUT");&lt;br /&gt;        try {&lt;br /&gt;            return Integer.parseInt(defaultSoTimeoutStr);&lt;br /&gt;        } catch(RuntimeException ex) {&lt;br /&gt;            return 5000;    // default to 5 seconds&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;    &lt;br /&gt;    @Override&lt;br /&gt;    protected void connect(SocketAddress endpoint, int timeout) throws IOException {&lt;br /&gt;        super.connect(endpoint, timeout == 0 ? defaultSoTimeout : timeout);&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    @Override&lt;br /&gt;    protected void connect(String host, int port) throws UnknownHostException, IOException {&lt;br /&gt;        setTimeoutIfNecessary();&lt;br /&gt;        super.connect(host, port);&lt;br /&gt;    }&lt;br /&gt;    &lt;br /&gt;    @Override&lt;br /&gt;    protected void connect(InetAddress address, int port) throws IOException {&lt;br /&gt;        setTimeoutIfNecessary();&lt;br /&gt;        super.connect(address, port);&lt;br /&gt;    }&lt;br /&gt;    &lt;br /&gt;    private void setTimeoutIfNecessary() throws SocketException {&lt;br /&gt;        int timeout = super.getTimeout();&lt;br /&gt;        &lt;br /&gt;        if (timeout == 0)&lt;br /&gt;            super.setOption(SO_TIMEOUT, defaultSoTimeout);&lt;br /&gt;        return;&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-4888878132253509738?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/4888878132253509738/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=4888878132253509738' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4888878132253509738'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4888878132253509738'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/09/no-more-infinitely-blocking-socket.html' title='No more infinitely blocking socket ?'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-8348964685212144201</id><published>2008-09-20T21:29:00.000-07:00</published><updated>2008-09-22T11:28:08.307-07:00</updated><title type='text'>When is NEVER ever ?</title><content type='html'>During one of today's &lt;a href="http://www.nofluffjuststuff.com/conference/seattle/2008/09/index.html"&gt;NFJS&lt;/a&gt; sessions, &lt;a href="http://www.infoq.com/minibooks/JTDS"&gt;Transaction Design Patterns&lt;/a&gt; by &lt;a href="http://www.nofluffjuststuff.com/conference/speaker/mark_richards.html"&gt;Mark Richards&lt;/a&gt;, the audience were asked when it would make sense to specify the transaction attribute &lt;a href="http://static.springframework.org/spring/docs/2.0.x/api/org/springframework/transaction/TransactionDefinition.html#PROPAGATION_NEVER"&gt;NEVER&lt;/a&gt; in a real-life application.  &lt;br /&gt;&lt;br /&gt;My immediate answer to this was that if a method is known to never get involved in a transactional context, then specifying &lt;a href="http://static.springframework.org/spring/docs/2.0.x/api/org/springframework/transaction/TransactionDefinition.html#PROPAGATION_NEVER"&gt;NEVER&lt;/a&gt; would allow the application to fail fast.  But what would be the practical circumstances where a method should never get involved in a transaction, to the extent of potentially causing an exception in production ?  And if there weren't really such circumstances, why not use the &lt;a href="http://static.springframework.org/spring/docs/2.0.x/api/org/springframework/transaction/TransactionDefinition.html#PROPAGATION_SUPPORTS"&gt;SUPPORTS&lt;/a&gt;  attribute instead ?  Asked Richard.&lt;br /&gt;&lt;br /&gt;On second thought, maybe we can use the NEVER attribute a lot more often and useful than it now is.  Let me explain.&lt;br /&gt;&lt;br /&gt;Consider the transaction attribute &lt;a href="http://static.springframework.org/spring/docs/2.0.x/api/org/springframework/transaction/TransactionDefinition.html#PROPAGATION_REQUIRES_NEW"&gt;REQUIRES_NEW&lt;/a&gt;, which basically creates a new transaction if one doesn't already exist.   But what if there already exists a transaction ?  Instead of throwing an exception, like NEVER, it would suspend the current transaction and creates a new one.  However, suspending a transaction is both expensive and usually not the intended semantics, as Richard pointed out.  &lt;br /&gt;&lt;br /&gt;So wouldn't it be nice if there exists a transaction attribute&lt;blockquote&gt;&lt;span style="font-weight:bold;"&gt;&lt;span style="font-style:italic;"&gt;NEVER_REQUIRES_NEW&lt;/span&gt;&lt;/span&gt;&lt;/blockquote&gt; that would both guarantee there is no pre-existing transaction when a method is invoked, and then proceed to always create a new transaction ?  But there is no such transaction attribute either in &lt;a href="http://docs.sun.com/app/docs/doc/819-3669/6n5sg7cm3?a=view"&gt;JEE 5&lt;/a&gt;, nor in &lt;a href="http://static.springframework.org/spring/docs/2.0.x/api/org/springframework/transaction/TransactionDefinition.html"&gt;Spring&lt;/a&gt;.&lt;br /&gt;&lt;br /&gt;Here is what I think could achieve the NEVER_REQUIRES_NEW transaction semantics, assuming the service method name is M:&lt;ol&gt;&lt;li&gt;Split method M into M1 and M2, and move the implementation of M to M2;&lt;br /&gt;&lt;li&gt;M1 is a no-op annotated with the transaction attribute NEVER, whereas M2 is annotated with REQUIRES_NEW;&lt;br /&gt;&lt;li&gt;Provide a proxy service that always invokes M1 followed by M2, exposing in turn to the client only a service method M without any transactional annotation;&lt;br /&gt;&lt;/ol&gt;Now when client invokes M, the proxy would in turn invoke M1 that guarantees there is no pre-existing transaction, and then invoke M2 which would always create a new transaction, effectively resulting in NEVER_REQUIRES_NEW!&lt;br /&gt;&lt;br /&gt;Is this yet another Transaction Design Pattern ?  The use of NEVER could be forever changed :)&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-8348964685212144201?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/8348964685212144201/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=8348964685212144201' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/8348964685212144201'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/8348964685212144201'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/09/when-is-never-ever.html' title='When is NEVER ever ?'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-5320005032909750078</id><published>2008-09-06T23:03:00.000-07:00</published><updated>2008-09-06T23:32:37.816-07:00</updated><title type='text'>Visiting Every Permutation ?</title><content type='html'>Given a set of objects, sometimes it's useful to find out all the &lt;a href="http://en.wikipedia.org/wiki/Permutation"&gt;permutation&lt;/a&gt; of these objects, and perform some action upon each permutation.  The order of the permutation generation would preferably be in some natural order such as lexicographic i.e. the order they would appear if they were sorted numerically.&lt;br /&gt;&lt;br /&gt;How would you go about writing such utility efficiently in Java ?&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;One possible answer:&lt;/span&gt;&lt;blockquote&gt;&lt;pre&gt;public class Permutation&amp;lt;T&gt; {&lt;br /&gt;    public static interface Visitor&amp;lt;T&gt; {&lt;br /&gt;        /** Visits each permutation of objects. */&lt;br /&gt;        public void visit(T[] entry);&lt;br /&gt;    }&lt;br /&gt;    private final T[] objects;&lt;br /&gt;    private T tmp;&lt;br /&gt;    private final Visitor&amp;lt;T&gt; visitor;&lt;br /&gt;    &lt;br /&gt;    /**&lt;br /&gt;     * @param objects set of n objects&lt;br /&gt;     * @param visitor used to visit each permutation&lt;br /&gt;     */&lt;br /&gt;    public Permutation(T[] objects, Visitor&amp;lt;T&gt; visitor) {&lt;br /&gt;        this.objects = objects.clone();&lt;br /&gt;        this.visitor = visitor;&lt;br /&gt;    }&lt;br /&gt;    &lt;br /&gt;    public void compute() { doCompute(0); }&lt;br /&gt;    &lt;br /&gt;    private void doCompute(final int pos) {&lt;br /&gt;        if (pos == objects.length) {&lt;br /&gt;            visitor.visit(objects);&lt;br /&gt;            return;&lt;br /&gt;        }&lt;br /&gt;&lt;br /&gt;        doCompute(pos+1);&lt;br /&gt;        &lt;br /&gt;        for (int i=pos+1; i &lt; objects.length; i++) {&lt;br /&gt;            swap(pos, i);&lt;br /&gt;            doCompute(pos+1);&lt;br /&gt;        }&lt;br /&gt;        &lt;br /&gt;        if (pos &gt; 0)&lt;br /&gt;            for (int i=pos+1; i &lt; objects.length; i++)&lt;br /&gt;                swap(i-1, i);&lt;br /&gt;    }&lt;br /&gt;    &lt;br /&gt;    private void swap(int p1, int p2) {&lt;br /&gt;        tmp = objects[p1];&lt;br /&gt;        objects[p1] = objects[p2];&lt;br /&gt;        objects[p2] = tmp;&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;&lt;span style="font-weight:bold;"&gt;Demo:&lt;/span&gt;&lt;blockquote&gt;&lt;pre&gt;Visitor&amp;lt;Character&gt; visitor = new Visitor&amp;lt;Character&gt;() {&lt;br /&gt;    private Set&amp;lt;String&gt; set = new HashSet&amp;lt;String&gt;();&lt;br /&gt;&lt;br /&gt;    @Override&lt;br /&gt;    public void visit(Character[] entry) {&lt;br /&gt;        String s = Arrays.toString(entry);&lt;br /&gt;        set.add(s);&lt;br /&gt;        System.out.println(set.size() + ": " + s);&lt;br /&gt;    }&lt;br /&gt;};&lt;br /&gt;String s = "abc";&lt;br /&gt;Character[] ca = new Character[s.length()];&lt;br /&gt;&lt;br /&gt;for (int i = s.length() - 1; i &gt; -1; i--)&lt;br /&gt;    ca[i] = s.charAt(i);&lt;br /&gt;new Permutation&amp;lt;Character&gt;(ca, visitor).compute();&lt;/pre&gt;&lt;/blockquote&gt;Would yield:&lt;blockquote&gt;&lt;pre&gt;1: [a, b, c]&lt;br /&gt;2: [a, c, b]&lt;br /&gt;3: [b, a, c]&lt;br /&gt;4: [b, c, a]&lt;br /&gt;5: [c, a, b]&lt;br /&gt;6: [c, b, a]&lt;/pre&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-5320005032909750078?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/5320005032909750078/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=5320005032909750078' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5320005032909750078'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5320005032909750078'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/09/visiting-every-permutation.html' title='Visiting Every Permutation ?'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-4618839521770669267</id><published>2008-09-02T23:22:00.000-07:00</published><updated>2008-09-03T20:11:11.756-07:00</updated><title type='text'>Visiting Every Combination ?</title><content type='html'>Given a set of objects, sometimes it's useful to find out all the &lt;a href="http://en.wikipedia.org/wiki/Combination"&gt;combination&lt;/a&gt; of these objects of a given size, and perform some action upon each combination.  For example, given a set of letters "abcde", print out all the combination of 4 letters from the set.&lt;br /&gt;&lt;br /&gt;How would you go about writing such utility efficiently in Java ?&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;One possible answer:&lt;/span&gt;&lt;blockquote&gt;&lt;pre&gt;public class Combination&amp;lt;T&gt; {&lt;br /&gt;    public static interface Visitor&amp;lt;T&gt; {&lt;br /&gt;        /** Visits each k-combination of objects. */&lt;br /&gt;        public void visit(T[] entry);&lt;br /&gt;    }&lt;br /&gt;    private final T[] objects; // Given set of objects&lt;br /&gt;    private final T[] entry;   // each combination of size k&lt;br /&gt;    private final Visitor&amp;lt;T&gt; visitor;&lt;br /&gt;&lt;br /&gt;    /**&lt;br /&gt;     * @param objects set of n objects&lt;br /&gt;     * @param k size of each combination&lt;br /&gt;     * @param visitor used to visit each combination&lt;br /&gt;     */&lt;br /&gt;    public Combination(T[] objects, int k, Visitor&amp;lt;T&gt; visitor) {&lt;br /&gt;        this.objects = objects.clone();&lt;br /&gt;        entry = Arrays.copyOf(this.objects, k);&lt;br /&gt;        this.visitor = visitor;&lt;br /&gt;    }&lt;br /&gt;&lt;br /&gt;    public void compute() { doCompute(0, 0); }&lt;br /&gt;&lt;br /&gt;    private void doCompute(int pos, int entryPos) {&lt;br /&gt;        if (entryPos == entry.length) {&lt;br /&gt;            visitor.visit(entry);&lt;br /&gt;            return;&lt;br /&gt;        }&lt;br /&gt;        // (entry.length - entryPos) is the remaining size&lt;br /&gt;        for (int i = pos, end = objects.length - (entry.length - entryPos) + 1; i &lt; end; i++) {&lt;br /&gt;            entry[entryPos] = objects[i];&lt;br /&gt;            doCompute(i + 1, entryPos + 1);&lt;br /&gt;        }&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;&lt;span style="font-weight:bold;"&gt;Demo:&lt;/span&gt;&lt;blockquote&gt;&lt;pre&gt;Visitor&amp;lt;Character&gt; visitor = new Visitor&amp;lt;Character&gt;() {&lt;br /&gt;    private Set&amp;lt;String&gt; set = new HashSet&amp;lt;String&gt;();&lt;br /&gt;&lt;br /&gt;    @Override&lt;br /&gt;    public void visit(Character[] entry) {&lt;br /&gt;        String s = Arrays.toString(entry);&lt;br /&gt;        set.add(s);&lt;br /&gt;        System.out.println(set.size() + ": " + s);&lt;br /&gt;    }&lt;br /&gt;};&lt;br /&gt;String s = "abcde";&lt;br /&gt;Character[] ca = new Character[s.length()];&lt;br /&gt;&lt;br /&gt;for (int i = s.length() - 1; i &gt; -1; i--)&lt;br /&gt;    ca[i] = s.charAt(i);&lt;br /&gt;&lt;br /&gt;final int size = 4;&lt;br /&gt;new Combination&amp;lt;Character&gt;(ca, size, visitor).compute();&lt;/pre&gt;&lt;/blockquote&gt;Would yield:&lt;blockquote&gt;&lt;pre&gt;1: [a, b, c, d]&lt;br /&gt;2: [a, b, c, e]&lt;br /&gt;3: [a, b, d, e]&lt;br /&gt;4: [a, c, d, e]&lt;br /&gt;5: [b, c, d, e]&lt;/pre&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-4618839521770669267?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/4618839521770669267/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=4618839521770669267' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4618839521770669267'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4618839521770669267'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/09/visiting-every-combination.html' title='Visiting Every Combination ?'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-5066117563680214042</id><published>2008-08-05T12:46:00.000-07:00</published><updated>2008-08-23T16:57:41.975-07:00</updated><title type='text'>Root Cause Java Quiz</title><content type='html'>Can the following code leads to an endless loop ?&lt;blockquote&gt;&lt;pre&gt;    public static Throwable getRootCause(Throwable t) {&lt;br /&gt;        if (t == null)&lt;br /&gt;            return t;&lt;br /&gt;        Throwable cause = t.getCause();&lt;br /&gt;        &lt;br /&gt;        if (cause == null)&lt;br /&gt;            return t;&lt;br /&gt;        return getRootCause(cause);&lt;br /&gt;    }&lt;br /&gt;&lt;/pre&gt;&lt;/blockquote&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Answer:&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;Don't try this at home ;)&lt;blockquote&gt;&lt;pre&gt;        Exception ex1 = new Exception("ex1");&lt;br /&gt;        Exception ex2 = new Exception("ex2");&lt;br /&gt;        ex1.initCause(ex2);&lt;br /&gt;        ex2.initCause(ex1);&lt;br /&gt;        getRootCause(ex1);&lt;/pre&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-5066117563680214042?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/5066117563680214042/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=5066117563680214042' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5066117563680214042'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5066117563680214042'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/08/endless-root-cause-in-java.html' title='Root Cause Java Quiz'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-4049311265692328948</id><published>2008-07-12T17:59:00.000-07:00</published><updated>2008-07-13T19:41:30.253-07:00</updated><title type='text'>Java Enum Puzzler</title><content type='html'>What does the following print ?&lt;blockquote&gt;&lt;pre&gt;public enum FooEnum {&lt;br /&gt;    FOO { @Override public void bar() {} };&lt;br /&gt;    public abstract void bar();&lt;br /&gt;    &lt;br /&gt;    public static void main(String...args) {&lt;br /&gt;        System.out.println(FOO.getClass().isEnum());&lt;br /&gt;    }&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;&lt;span style="font-weight:bold;"&gt;Answer:&lt;/span&gt;&lt;br /&gt;&lt;br /&gt;FOO is an enum value in FooEnum.  The class of FOO must therefore be an enum, and it should print "true".  Right ?  If you give it a try, surprisingly it will print "false".  Why ?&lt;br /&gt;&lt;br /&gt;Peeking into the JDK source code of Class.java,&lt;blockquote&gt;&lt;pre&gt;public boolean isEnum() {&lt;br /&gt;    // An enum must both directly extend java.lang.Enum and have&lt;br /&gt;    // the ENUM bit set; classes for specialized enum constants&lt;br /&gt;    // don't do the former.&lt;br /&gt;    return (this.getModifiers() &amp; ENUM) != 0 &amp;&amp; &lt;br /&gt;            this.getSuperclass() == java.lang.Enum.class;&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;Now if you tried to print out the super class of FOO.class, it would print FooEnum.class, rather than Enum.class.  The comparison of the super class of FOO.class against Enum.class would therefore fail in the second condition of the return statement.&lt;br /&gt;&lt;br /&gt;To me, this looks like a bug either in the javac compiler, or in the implementation of Class.isEnum().  &lt;br /&gt;&lt;br /&gt;Why is it probably a bug in the javac compiler ?  Well, shouldn't the super class of FOO.class be Enum.class, instead of FooEnum.class ?  (Special thanks to Dhanji&amp;nbsp;R.&amp;nbsp;Prasanna for pointing this out.)  &lt;br /&gt;&lt;br /&gt;Why is it probably a bug in Class.isEnum() ?  Well, shouldn't it recursively check all the super classes of FOO.class for Enum.class, instead of just the direct super class ?  And why does it need to compare the super class with Enum.class at all, when there is already the checking for the ENUM class modifier ?&lt;br /&gt;&lt;br /&gt;What do you think ?&lt;br /&gt;&lt;br /&gt;&lt;span style="font-style:italic;"&gt;Update on 7/13/2008:&lt;/span&gt; Please vote for bug &lt;a href="http://bugs.sun.com/view_bug.do?bug_id=6710708"&gt;6710708&lt;/a&gt;.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-4049311265692328948?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/4049311265692328948/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=4049311265692328948' title='1 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4049311265692328948'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4049311265692328948'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/07/java-enum-puzzler.html' title='Java Enum Puzzler'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>1</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-4391690991396694181</id><published>2008-07-11T03:11:00.000-07:00</published><updated>2008-07-12T11:53:42.615-07:00</updated><title type='text'>Dumping a JavaBean as name/value pairs ?</title><content type='html'>Sometimes it's useful to deeply dump out the properties of a complex JavaBean as name/value pairs, perhaps for debugging purposes, even when none of the toString methods of the classes involved are defined.  This is especially the case when the JavaBean classes are written by a third party.&lt;br /&gt;&lt;br /&gt;Now how would you go about doing that ?&lt;br /&gt;&lt;br /&gt;How about using the Jarkarta commons-lang's &lt;a href="http://commons.apache.org/lang/api/org/apache/commons/lang/builder/ToStringBuilder.html#reflectionToString%28java.lang.Object%29"&gt;ToStringBuilder.reflectionToString&lt;/a&gt; method ?  It doesn't cut it, as it relies on the toString method of the individual classes involved.&lt;br /&gt;&lt;br /&gt;How about &lt;a href="http://java.sun.com/j2se/1.5.0/docs/api/java/beans/XMLEncoder.html"&gt;XMLEncoder&lt;/a&gt; or &lt;a href="http://xstream.codehaus.org/"&gt;XStream&lt;/a&gt; ?  They work pretty nicely.  However, by default XStream generates not just the public properties but all other fields as well.  In both cases, the generated XML would need to be further transformed into name/value pairs.&lt;br /&gt;&lt;br /&gt;Another way I can think of is to take advantage of the latest &lt;a href="http://beanlib.sourceforge.net/3.3.0beta18/api/net/sf/beanlib/spi/BeanSourceHandler.html"&gt;BeanSourceHandler&lt;/a&gt; SPI as a side effect of performing a deep clone via the open-source library &lt;a href="http://beanlib.sourceforge.net/"&gt;Beanlib&lt;/a&gt; (beanlib-3.3.0beta18).  What do I mean ?  Here is an example:&lt;blockquote&gt;&lt;pre&gt;Object bean = ...&lt;br /&gt;// Dump out the entire JavaBean&lt;br /&gt;// when none of the toString methods are defined.&lt;br /&gt;BeanReplicator.newBeanReplicatable(customTransformer()).replicateBean(bean);&lt;br /&gt;&lt;br /&gt;private static BeanTransformerSpi customTransformer() {&lt;br /&gt;    BeanTransformerSpi beanTransformer = BeanTransformer.newBeanTransformer();&lt;br /&gt;    return beanTransformer.initBeanSourceHandler(new BeanSourceHandler() {&lt;br /&gt;        public void handleBeanSource(Object fromBean, Method readerMethod, Object propertyValue) {&lt;br /&gt;            System.out.println(&lt;br /&gt;                String.valueOf(fromBean.getClass().getSimpleName() + "."&lt;br /&gt;                + readerMethod.getName() + "=" + propertyValue));&lt;br /&gt;        }&lt;br /&gt;    });&lt;br /&gt;}&lt;/pre&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-4391690991396694181?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/4391690991396694181/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=4391690991396694181' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4391690991396694181'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/4391690991396694181'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/07/how-do-dump-javabean.html' title='Dumping a JavaBean as name/value pairs ?'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-5096036793865008557</id><published>2008-07-02T10:32:00.000-07:00</published><updated>2008-07-02T10:51:39.580-07:00</updated><title type='text'>Little Java Quiz - File loaded from classpath</title><content type='html'>Given:&lt;br /&gt;&lt;ol&gt;&lt;li&gt;a file with a given name;&lt;/li&gt;&lt;li&gt;the file is located in the file system;&lt;/li&gt;&lt;li&gt;the file can be loaded via the classpath;&lt;/li&gt;&lt;/ol&gt;How can the code figure out the physical location (ie absolute path) of the file ?&lt;br /&gt;&lt;br /&gt;(Don't peek if you want to give it a try!)&lt;br /&gt;&lt;br /&gt;&lt;span style="font-weight:bold;"&gt;Answer&lt;/span&gt;:&lt;blockquote&gt;&lt;pre&gt;    String filePath = Thread.currentThread()&lt;br /&gt;                            .getContextClassLoader()&lt;br /&gt;                            .getResource(filename)&lt;br /&gt;                            .getFile();&lt;/pre&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-5096036793865008557?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/5096036793865008557/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=5096036793865008557' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5096036793865008557'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5096036793865008557'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/07/little-java-quiz-file-loaded-from.html' title='Little Java Quiz - File loaded from classpath'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-1736161014725363666</id><published>2008-04-11T00:20:00.000-07:00</published><updated>2008-04-11T12:11:29.879-07:00</updated><title type='text'>Tomcat 5.5 SSL Programming Puzzle</title><content type='html'>Assuming SSL client side authentication is enabled in Tomcat 5.5, how can a webapp go about retrieving the underlying client's X509 certificate of the SSL socket ?  &lt;br /&gt;&lt;br /&gt;Browsing through the Tomcat source code, such information can be found in the SSL session, which unfortunately seems totally unreachable from the servlet layer.&lt;br /&gt;&lt;br /&gt;Well, thanks to reflection, below is one such solution.  Do you know of a better one ?&lt;br /&gt;&lt;br /&gt;&lt;blockquote&gt;&lt;pre&gt;    /** &lt;br /&gt;     * Returns the requester's X509 SSL certificate(s) of the given request;&lt;br /&gt;     * or null if no such certificate can be determined. &lt;br /&gt;     */&lt;br /&gt;    static X509Certificate[] getPeerCertificates(HttpServletRequest req) {&lt;br /&gt;        // rip open the tomcat specific request object to retrieve the peer SSL cert(s)&lt;br /&gt;        try &lt;br /&gt;        {   // Dig out the org.apache.catalina.connector.Request object&lt;br /&gt;            Field f = req.getClass().getDeclaredField("request");&lt;br /&gt;            f.setAccessible(true);&lt;br /&gt;            Object catalinaConnectorRequest = f.get(req);&lt;br /&gt;            &lt;br /&gt;            // Dig out the org.apache.coyote.Request object&lt;br /&gt;            // by invoking org.apache.catalina.connector.Request.getCoyoteRequest()&lt;br /&gt;            Method getCoyoteRequestMethod = catalinaConnectorRequest.getClass().getMethod("getCoyoteRequest");&lt;br /&gt;            Object coyoteRequest = getCoyoteRequestMethod.invoke(catalinaConnectorRequest);&lt;br /&gt;&lt;br /&gt;            // Dig out the proper class loader&lt;br /&gt;            Class coyoteRequestClass = coyoteRequest.getClass();&lt;br /&gt;            ClassLoader classLoader = coyoteRequestClass.getClassLoader();&lt;br /&gt;            &lt;br /&gt;            // Dig out the ActionCode class loaded by the approprate class loader&lt;br /&gt;            Class actionCodeClass = classLoader.loadClass("org.apache.coyote.ActionCode");&lt;br /&gt;            &lt;br /&gt;            // Refer to the ActionCode.ACTION_REQ_SSL_CERTIFICATE&lt;br /&gt;            Field actionReqSslCertField = actionCodeClass.getDeclaredField("ACTION_REQ_SSL_CERTIFICATE");&lt;br /&gt;            Object actionReqSslCert = actionReqSslCertField.get(null);&lt;br /&gt;            &lt;br /&gt;            // Invoke org.apache.coyote.Request.action(ActionCode.ACTION_REQ_SSL_CERTIFICATE, null)&lt;br /&gt;            Method actionMethod = coyoteRequestClass.getMethod("action", actionReqSslCert.getClass(), Object.class);&lt;br /&gt;            actionMethod.invoke(coyoteRequest, actionReqSslCert, null);&lt;br /&gt;            &lt;br /&gt;            // Dig out the SSLSupport class loaded by the approprate class loader&lt;br /&gt;            Class sslSupportClass = classLoader.loadClass("org.apache.tomcat.util.net.SSLSupport");&lt;br /&gt;            &lt;br /&gt;            // Refer to the SSLSupport.CERTIFICATE_KEY&lt;br /&gt;            Field sslSupportCertKeyField = sslSupportClass.getDeclaredField("CERTIFICATE_KEY");&lt;br /&gt;            Object sslSupportCertKey = sslSupportCertKeyField.get(null);&lt;br /&gt;            &lt;br /&gt;            // Invoke org.apache.coyote.Request.getAttribute(SSLSupport.CERTIFICATE_KEY)&lt;br /&gt;            Method getAttributeMethod = coyoteRequest.getClass()&lt;br /&gt;                                                     .getMethod("getAttribute", sslSupportCertKey.getClass());&lt;br /&gt;            return (X509Certificate[])getAttributeMethod.invoke(coyoteRequest, sslSupportCertKey);&lt;br /&gt;        } catch(Throwable t) {&lt;br /&gt;        }&lt;br /&gt;        return null;&lt;br /&gt;    }&lt;br /&gt;&lt;/pre&gt;&lt;/blockquote&gt;It turns out there is a much simpler way to solve this problem.  According to the spec (section SRV.4.7), if there is an SSL certificate associated with the request, it must be exposed by the servlet container to the servlet programmer as an array of objects of type java.security.cert.X509Certificate and accessible via a ServletRequest attribute of javax.servlet.request.X509Certificate.&lt;br /&gt;&lt;br /&gt;Thanks to Mark Thomas for pointing this out.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-1736161014725363666?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/1736161014725363666/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=1736161014725363666' title='2 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/1736161014725363666'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/1736161014725363666'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/04/tomcat-55-ssl-programming-puzzle.html' title='Tomcat 5.5 SSL Programming Puzzle'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>2</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-5748818964214717410</id><published>2008-04-03T10:00:00.000-07:00</published><updated>2008-04-03T16:16:17.873-07:00</updated><title type='text'>On Frugality</title><content type='html'>Be contra-variant in what you take, but covariant in what you give.  In other words, take less and give more.&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-5748818964214717410?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/5748818964214717410/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=5748818964214717410' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5748818964214717410'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/5748818964214717410'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/04/on-frugality.html' title='On Frugality'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-101065176066307256</id><published>2008-01-30T21:18:00.000-08:00</published><updated>2008-03-09T20:11:00.588-07:00</updated><title type='text'>Tuning JVM with ICMS</title><content type='html'>Some readings:&lt;br /&gt;&lt;br /&gt;  http://www.sun.com/bigadmin/content/submitted/cms_gc_logs.html&lt;br /&gt;  http://java.sun.com/docs/hotspot/gc5.0/gc_tuning_5.html&lt;br /&gt;  http://java.sun.com/docs/hotspot/gc1.4.2/example.html&lt;br /&gt;  http://blogs.sun.com/jonthecollector/entry/when_the_sum_of_the&lt;br /&gt;&lt;br /&gt;  http://java.sun.com/j2se/1.5.0/docs/guide/vm/gc-ergonomics.html&lt;br /&gt;  http://performance.netbeans.org/howto/jvmswitches/index.html&lt;br /&gt;  http://java.sun.com/javase/6/docs/technotes/guides/vm/cms-6.html&lt;br /&gt;&lt;br /&gt;  http://java.sun.com/performance/reference/whitepapers/tuning.html&lt;br /&gt;  http://blogs.sun.com/watt/resource/jvm-options-list.html&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-101065176066307256?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/101065176066307256/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=101065176066307256' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/101065176066307256'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/101065176066307256'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/01/tuning-jvm-with-icms.html' title='Tuning JVM with ICMS'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry><entry><id>tag:blogger.com,1999:blog-6715087.post-8774114376050287123</id><published>2008-02-15T15:43:00.000-08:00</published><updated>2008-02-16T18:11:25.383-08:00</updated><title type='text'>Some JMX Quizzes</title><content type='html'>&lt;ol&gt;&lt;li&gt;Where can you find out all those Platform MBean Object Names ?&lt;/li&gt;&lt;li&gt;How would you connect via JMX with username and password programmatically ?&lt;/li&gt;&lt;/ol&gt;Some possible answers:&lt;ol&gt;&lt;li&gt;Where can you find out all those Platform MBean Object Names ?&lt;/li&gt;&lt;blockquote&gt;&lt;pre&gt;&lt;a href="http://java.sun.com/j2se/1.5.0/docs/api/java/lang/management/ManagementFactory.html"&gt;java.lang.management.ManagementFactory&lt;/a&gt;&lt;/pre&gt;&lt;/blockquote&gt;&lt;li&gt;How would you connect via JMX with username and password programmatically ?&lt;/li&gt;&lt;/ol&gt;&lt;blockquote&gt;       &lt;pre&gt;    Map&amp;lt;String,String[]&gt; env = new HashMap&amp;lt;String,String[]&gt;();&lt;br /&gt;    env.put(JMXConnector.CREDENTIALS, new String[]{"username", "password"});&lt;br /&gt;    final String url = "service:jmx:rmi://" + host + "/jndi/rmi://" + host + ":" + port + "/jmxrmi";&lt;br /&gt;    JMXServiceURL jmxServiceUrl = new JMXServiceURL(url);&lt;br /&gt;    JMXConnector conn = JMXConnectorFactory.connect(jmxServiceUrl, env);&lt;br /&gt;    MBeanServerConnection mbsc = conn.getMBeanServerConnection();&lt;br /&gt;    ...&lt;/pre&gt;&lt;/blockquote&gt;&lt;div class="blogger-post-footer"&gt;&lt;img width='1' height='1' src='https://blogger.googleusercontent.com/tracker/6715087-8774114376050287123?l=hansonchar.blogspot.com' alt='' /&gt;&lt;/div&gt;</content><link rel='replies' type='application/atom+xml' href='http://hansonchar.blogspot.com/feeds/8774114376050287123/comments/default' title='Post Comments'/><link rel='replies' type='text/html' href='https://www.blogger.com/comment.g?blogID=6715087&amp;postID=8774114376050287123' title='0 Comments'/><link rel='edit' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/8774114376050287123'/><link rel='self' type='application/atom+xml' href='http://www.blogger.com/feeds/6715087/posts/default/8774114376050287123'/><link rel='alternate' type='text/html' href='http://hansonchar.blogspot.com/2008/02/where-to-find-those-platform-mbean.html' title='Some JMX Quizzes'/><author><name>Hanson Char</name><uri>http://www.blogger.com/profile/17880352604016760155</uri><email>noreply@blogger.com</email><gd:extendedProperty xmlns:gd='http://schemas.google.com/g/2005' name='OpenSocialUserId' value='12878261557857134843'/></author><thr:total xmlns:thr='http://purl.org/syndication/thread/1.0'>0</thr:total></entry></feed>