Odd practices in Java


There are a number of practices in Java which oddly baffle me. Here are but a few.

Using -Xmx and -Xms

The option -Xmx is widely used to set the maximum memory size. As noted in the Java HotSpot VM Options 
Options that begin with -X are non-standard (not guaranteed to be supported on all VM implementations), and are subject to change without notice in subsequent releases of the JDK.
 So you would think that such a widely used option would not be non-standard any more.  In fact there is a standard option -mx and similarly -ms. I don't know why these standard options are not use more widely, or even documented.

Using NIO for non-blocking IO only

Non blocking IO was a new feature of NIO for sockets.  However, the default behaviour for NIO Socket is blocking. Files are only blocking in NIO. NIO2 provides an asynchronous interface, but does it by passing your request off to an ExecutorService (which is cheating really because it doesn't anything do what you can't do better already)

Personally I prefer blocking NIO. Its is only suitable when you have a low number of binary connections, but it is an option which doesn't get enough press IMHO.

Using the 32-bit JVM to save memory

The amount of memory you save with a 32-bit JVM is far less than you might think. Modern 64-bit JVMs use 32-bit references by default for up to 32 GB heap sizes. It is unlikely you want to have a larger heap size (if only to avoid very long Full GC times)

The 32-bit JVM still has a smaller object header than the 64-bit JVM, but the difference is fairly small.
The 64-bit JVM can use more, larger registers (on AMD/Intel x64 systems) and a much larger address space allowing you have less memory limitations.

Using threads to make everything faster

Using multiple threads can increase your CPU utilisation and reduce the impact of IO latency. It doesn't solve all performance problems. It won't make your disks go faster, increase your network bandwidth, the size of your L3 cache, increase you CPU to main memory bandwidth or make your database significantly faster.

Similarly making everything concurrent won't make so much difference either. Do you need 1000 concurrent collections when you only have 8 cores? No matter how many threads you have, only 8 of them will be running at once, and if you have 1000 collections its quite unlikely that two will be using the same collection.

Use concurrency selectively for critical resources. Otherwise you risk not only increasing overhead and slowing down your application, but far worse is the increase in complexity you introduce.

More rantings to follow. ;)


  1. Some days ago I read an article which showed that NIO is often not really faster than the 'old' IO (Java library). Of course I cannot find it now. What is your experience?

    And do you have any numbers for the heap differences of 32 and 64 bit JVMs?

    The -Xmx thing is probably a 'meme' ;-)

  2. Here is an article I wrote comparing blocking NIO with blocking IO i.e. the same threading model. http://vanillajava.blogspot.co.uk/2010/07/java-nio-is-faster-than-java-io-for.html

    An article on object size in 32-bit vs 64-bit JVMs http://vanillajava.blogspot.co.uk/2011/07/java-getting-size-of-object.html

  3. Regarding using -Xmx and -Xms, they're widely used because it's recommended everywhere.

    For instance:
    - Maven: http://maven.apache.org/download.html#Installation (Add the MAVEN_OPTS environment variable to specify JVM properties, e.g. export MAVEN_OPTS="-Xms256m -Xmx512m")

    - Tunning IBM GC in WAS 8: http://www.ibm.com/developerworks/websphere/techjournal/1106_bailey/1106_bailey.html#sec-ng ("The minimum and maximum heap sizes can be modified by specifying -Xms and -Xmx respectively.")

    - Using (IBM) Memory Analyzer: http://www.ibm.com/developerworks/java/library/j-memoryanalyzer/index.html#N107ED ("Memory Analyzer itself may run out of memory. For the Eclipse MAT, edit -Xmx in the MemoryAnalyzer.ini ")

  4. @Javier, the question is; why is the non standard options recommended everywhere (even in the java man page) when there are standard options?

  5. > In fact there is a standard option -mx and similarly -ms
    There is? Where? I can't find anything in the documentation:

    Am I missing something?

  6. You might think so, except use of -mx and -ms https://www.google.co.uk/search?q=java+"-mx" dates back as far as 1999 https://groups.google.com/forum/?fromgroups#!topic/comp.lang.java.help/Ab1fua6AzGA

  7. Most of the articles on the performance of NIO only consider non-blocking NIO (which is one of my gripes) It appears to me that that non-blocking NIO doesn't perform as well for a modest number of connections << 1000, but scales better > 10,000 connections.

    For the tests I have done, comparing blocking IO and blocking NIO for a modest number of connections < 1000, the blocking NIO was faster.

  8. Hi, Peter, I would like to have an archive of all your posts on your blog to review offline, so I make a list in the classic format, but I can only access the post from 02May2010, in additionI want to have access to comments that are while important ... Is there another way to achieve what I want?

  9. Hi Peter! Congrats for your blog, very informative! Would you have a saying about this => http://stackoverflow.com/questions/12099446/java-nio-selector-minimum-possible-latency


Post a Comment

Popular posts from this blog

Low Latency Microservices, A Retrospective

Unusual Java: StackTrace Extends Throwable

System wide unique nanosecond timestamps