Print assembly for Java

The modern openjdk’s JVM is able to print assembly for generated machine code – see Oracle’s blog post.

To start working with this option you need hsdis plugin, available here.

Then put the downloaded library to the location your OS aware of.
E.g. if you’re using linux all you need is to update LD_LIBRARY_PATH:

export LD_LIBRARY_PATH="$LD_LIBRARY_PATH:/home/alex/bin/hsdis"

Then you must be able to start java with the PrintAssembly flag:

/usr/lib/jvm/java-6-sun/bin/java -XX:+UnlockDiagnosticVMOptions -XX:+PrintAssembly -server -cp . App

The dissassembled output might look as follows:

0xb3a15f0f: jmp 0xb3a15f1b ;*invokespecial RangeCheck
; - java.util.ArrayList::get@2 (line 322)
; - App$Finder::findSolution@33 (line 243)
; - App$Finder::findSolution@182 (line 263)
; - App$Finder::findSolution@182 (line 263)
0xb3a15f11: mov %eax,%ecx
0xb3a15f13: jmp 0xb3a15f1b ;*invokespecial RangeCheck
Total: 13211984ns
; - java.util.ArrayList::get@2 (line 322)
; - App$Finder::findSolution@33 (line 243)
; - App$Finder::findSolution@182 (line 263)
0xb3a15f15: mov %eax,%ecx
0xb3a15f17: jmp 0xb3a15f1b ;*invokespecial RangeCheck
; - java.util.ArrayList::get@2 (line 322)
; - App$Finder::findSolution@33 (line 243)
0xb3a15f19: mov %eax,%ecx ;*synchronization entry
; - App$Finder::findSolution@-1 (line 236)
0xb3a15f1b: add $0x68,%esp
0xb3a15f1e: pop %ebp
0xb3a15f1f: jmp 0xb3a11da0 ;*return
; - App$Finder::findSolution@27 (line 240)
; {runtime_call}
0xb3a15f24: hlt
0xb3a15f25: hlt

Tuning Intellij Idea

First of all consider changing idea.vmoptions.
idea.vmoptions is a text file with a list of JVM settings, it’s usually found in the bin folder in the Idea installation folder. This file can be open in any text editor.

The following settings increase performance drastically on Sun JVM 1.6:

-server
-Xms128m
-Xmx512m
-XX:MaxPermSize=250m
-XX:ReservedCodeCacheSize=64m
-XX:+UseConcMarkSweepGC
-XX:+AggressiveOpts
-XX:+CMSClassUnloadingEnabled
-XX:+CMSIncrementalMode
-XX:+CMSIncrementalPacing
-XX:CMSIncrementalDutyCycleMin=0
-XX:-TraceClassUnloading

Notice, that I enabled concurrent mark-sweep GC (in theory it’d be faster than others on 1.6) and aggressive optimizations as well as server JVM and I don’t use assertions (no `-ea’ switch).

I tested these on x86 linux with Idea Community edition of build 111.69

As for appearance I’d suggest using Nimbus theme (Settings -> Appearance -> Look and Feel).

That’s how idea looks on my Ubuntu:

Idea 11 Community Edition on Ubuntu

Full screenshot is available here.

P.S.: For Mac OS X users:
There is no idea.vmoptions file on Mac OS X.
In order to modify the mentioned JVM settings, you’d go to the application’s package contents, then open the inner “Contents” folder and then open Info.plist (just click on it and the standard plist editor will be opened). In the opened plist editor consider changing Java > VMOptions key as given above.
You may copy-and-paste the following value I use on my Mac laptop:

-Xverify:none -XX:+UseConcMarkSweepGC -XX:+AggressiveOpts -XX:+CMSClassUnloadingEnabled -XX:+CMSIncrementalMode -XX:+CMSIncrementalPacing -XX:CMSIncrementalDutyCycleMin=0 -XX:-TraceClassUnloading -Xbootclasspath/a:../lib/boot.jar

Note, that you may want to make Idea start in 32-bit mode to reduce the memory consumption and increase the overall IDE performance. Just ctrl-click on the application icon in the “Applications” folder and click on the checkbox “Open in 32-bit mode”.

After doing so Idea starts in 1 (ONE) second or so on my Mac Book Pro!

instanceof vs Visitor

I always was curious on how effective is visitor pattern vs instanceof when it comes to detect whether the given base implements certain interface or not.

I had 7 interface classes and visitor for all of these, and 7 concrete implementations, then I tested instanceof and visitor pattern on a large collection of randomly picked instances of these classes, the timing for 100000 objects was as follows on my machine (best value is taken for several interations of both benchmarks, the less is of course the better):

instanceof: 5.055 sec
visitor: 3.511 sec

The testing code snippets are as follows:

// for instanceof:
    public static int measureInstanceOf(Node[] nodes) {
        int litCount = 0;

        for (int i = 0; i < N; ++i) {
            if (nodes[i] instanceof Literal) {
                ++litCount;
            }
        }

        return litCount;
    }

// for visitor:
    public static final class LiteralCheckerVisitor implements NodeVisitor {
        boolean isLiteral = false;

        public void visitMarker(Marker marker) {}
        // other methods are similar to the given above and skipped

        public void visitLiteral(Literal literal) { isLiteral = true; }
    }

    public static int measureVisitor(Node[] nodes) {
        int litCount = 0;
        final LiteralCheckerVisitor visitor = new LiteralCheckerVisitor();

        for (int i = 0; i < N; ++i) {
            // equivalent of instanceof Literal
            visitor.isLiteral = false;
            nodes[i].accept(visitor);
            if (visitor.isLiteral) {
                ++litCount;
            }
        }

        return litCount;
    }

As for java version:

java version "1.6.0_24"
Java(TM) SE Runtime Environment (build 1.6.0_24-b07-334-10M3326)
Java HotSpot(TM) 64-Bit Server VM (build 19.1-b02-334, mixed mode)

The resolution is quite simple - try to avoid instanceof, at least in time-critical code. It's usage often indicates a misunderstanding of the OOP principles and often may result in bad design (and bad performance as well as higher maintenance costs).

Create self-sufficient JAR with maven

After getting stuck several times with maven assembly plugin I decided to make a note on how to create self-sufficient jar with maven. Self-sufficiency implies jar to include all the required dependencies so it can be started with java without specifying extra classpaths.

<build>
    <plugins>
        <!-- Packaging configuration -->
        <plugin>
            <artifactId>maven-assembly-plugin</artifactId>
            <configuration>
                <archive>
                    <manifest>
                        <addClasspath>true</addClasspath>
                        <mainClass>com.mysite.App</mainClass>
                    </manifest>
                </archive>
                <descriptorRefs>
                    <descriptorRef>jar-with-dependencies</descriptorRef>
                </descriptorRefs>
            </configuration>
        </plugin>
    </plugins>
</build>

Then you’ll be able to create self-sufficient jar:

mvn clean package assembly:assembly

context:annotation-config for StaticApplicationContext

For some reason I’m unable to use XML configuration for spring in the current project (and thus ClassPathXmlApplicationContext) – don’t ask me why :)
So I’ve to specify the entire configuration in code (by using StaticApplicationContext.registerSingleton).

The question is – how to make StaticApplicationContext work as if “annotation-config” is specified to make application context process annotated fields, methods (e.g. @Resource, @PostConstruct, etc.)?

After digging in spring javadocs it turns out to be very simple:

final StaticApplicationContext context = new StaticApplicationContext();

context.registerSingleton("beanPostProcessor", CommonAnnotationBeanPostProcessor.class);
context.registerSingleton("superior", SuperiorImpl.class);
context.registerSingleton("inferior", InferiorImpl.class);

context.refresh(); // Refresh is mandatory before any getBean invocation, otherwise bean processors won't work

final Superior superior = context.getBean(Superior.class);

The most important line is where CommonAnnotationBeanPostProcessor is registered in the DI context.

The spring documentation states regarding this class:

NOTE: A default CommonAnnotationBeanPostProcessor will be registered by the “context:annotation-config” and “context:component-scan” XML tags. Remove or turn off the default annotation configuration there if you intend to specify a custom CommonAnnotationBeanPostProcessor bean definition!


NOTE: Annotation injection will be performed before XML injection; thus the latter configuration will override the former for properties wired through both approaches.

How to write and debug your own annotations processor.

This is a short but comprehensive guide on how to write and debug your own annotations processor (assuming you are using Java 6, should work on Java 7 as well).

  • Create jar where your annotations processor will reside, say ann-proc.jar (Just define annotation processor class).You may want to add dependency to the JDK’s tools.jar in case you wanna use sun-specific code model entities:

    <dependency>
    <groupId>com.sun</groupId>
    <artifactId>tools</artifactId>
    <version>1.6.0</version>
    <scope>system</scope>
    <systemPath>${java.home}/../lib/tools.jar</systemPath>
    </dependency>

  • Create (or proceed to) another jar (say my.jar) you want to process with annotations processor, add annotations you want to process.
  • Add the following file (which in fact is a SPI configuration file) to my.jar resources folder

    resources
    |
    + /META-INF/services
    |
    + javax.annotation.processing.Processor

    The contents of this file would look as follows:

    com.ann.proc.processor.MyAnnotationProcessor

  • That’s it, do mvn clean install on the my.jar package having installed ann-proc.jar and see the effect.If you want to debug your annotations processor, you may use mvnDebug, say do mvnDebug clean compile in the my.jar root folder and attach your IDE to the 8000 debug port.

Ugly Netbeans font rendering on Ubuntu Linux

Netbeans fonts rendering may look ugly on the latest Ubuntu.
The following configuration does the trick for me (file $netbeans/etc/netbeans.conf, see part in bold):

# Options used by NetBeans launcher by default, can be overridden by explicit
# command line switches:
netbeans_default_options=”-J-client -J-Xss2m -J-Xms32m -J-XX:PermSize=32m -J-Dapple.laf.useScreenMenuBar=true -J-Dapple.awt.graphics.UseQuartz=true -J-Dsun.java2d.noddraw=true -J-Dswing.aatext=true -J-Dawt.useSystemAAFontSettings=lcd_hrgb

Checked with openjdk, it probably won’t work for “older” sun JDK.

Spring and AspectJ

For those who uses Spring 3.0.5:

Spring 3.0.5 doesn’t work with aspectjweaver 1.6.10+ due to AssertionError at org.aspectj.weaver.UnresolvedType.nameToSignature!

E.g. if you use aspects in your spring config with, say, jdbc:initalize-database configuration clause, most likely you’ll get assertion error in your JUnit test what uses such a config.

The possible workaround would be to switch to aspectjweaver of version 1.6.9.

Block internet access for application in Mac OS X

There is a wonderful set of native utilities named “sandbox”. These utilities include service sandboxd that, for example, prevents newly downloaded applications from being started immediately.

In order to block a particular application from accessing internet (but without turning off all the networking services) you may use “sandbox-exec” utility.

First of all, create sandbox profile for the particular application (say nonet.sb in your home folder):
(version 1)
(allow default)
(deny network*)

Then, you may start application in the sandboxed mode, where it is denied to access internet, e.g. as follows:

sandbox-exec -f /Users/alex/nonet.sb /Applications/Skype.app/Contents/MacOS/Skype

The example given above applies sandbox profile /Users/alex/nonet.sb to the Skype application.

Voila!

P.S.: If you quit sandboxed application and then start it again without applying the sandbox profile, the application will not be denied from accessing internet.

P.P.S.:
More on the sandbox utility:

Restlet’s JAX RS lacks custom converters

I published earlier how to use Restlet framework with Spring over its JAX RS frontend.

Unfortunately, there is no simple way to specify custom JSON converter for certain types, say java.util.Date (e.g. if you want to serialize it to ISO 8601-compatible string representation).
In order to support that you need either to write a custom MessageBodyConverter or serialize objects directly to string in your JAX RS resource.

I’m gonna try Apache CXF as it looks promising and flexible in such an aspect.