
I'm all for supporting open-source software but there are limits. I've recently
switched to using Ubuntu on my main machine at home and have run into two bugs in the same piece of open-source software.
If you are a regular reader of this blog then you are probably aware that I do most of my software development using Java. A default install of Ubuntu (10.10) includes the OpenJDK based IcedTea version of Java 6. This is a version of Java that is covered by an open-source license -- which is in comparison to the Sun/Oracle version of Java for which you can read the source but which was not covered by an open-source licence (it's now "mostly" covered by GPL v2 with the classpath exception). I've never really understood the philosophical argument behind IcedTea and the need for a clean room implementation of Java, although Oracle's recent attack on Android provides some explanation. Anyway, given that it was the default installation of Java I was willing to give it a try. Within minutes though I'd found two show stopping bugs and so have switched back to using the reliable Sun/Oracle release of Java 6.
The first bug is visual and one that I knew existed in earlier versions of IcedTea but which I hoped had been fixed by now. In essence the ImageIO JPEG reader in IcedTea doesn't properly handle JPEG images with embedded colour profiles. What you end up with is an image that looks like a a photographic negative rather than the image you tried to load. This bug basically means that you can't use IcedTea for any application that allows users to load arbitrary JPEG files. For me this means I can't recommend it for running
Convert4Frame,
TagME,
PhotoGrid or
3DAssembler. Also I can't use IcedTea to run the tomcat server in which I host my
cookbook web app. What is really annoying about this bug is that it was originally in the main Sun/Oracle distribution, reported all the way back in 2003, but was fixed in Java 5 update 4, you can read all about it in the
bug report. If the open-source version can't fix a bug that is around eight years old then why do they even bother!
The second bug is a little stranger but no less annoying. The
documentation for the method
ClassLoader.loadClass(String name)
states that either it returns the resulting
Class
object or throws a
ClassNotFoundException
if (wait for it) the class was not found. That all seems perfectly logical to me. Unfortunately there appears to be at least one situation in which IcedTea returns
null
instead of throwing an exception when the class cannot be found.
I distribute a lot of the open-source Java software that I develop in my spare time via Web Start and once I had Ubuntu up and running I thought I'd check Java by launching
3DAssembler. Unfortunately it failed to load and gave me a rather strange
NullPointerException
. After a bit of digging around (the version of the app on my website doesn't match my development version and hence the line numbers were out) I eventually tracked the problem back to this try/catch block.
1 2 3 4 5 6 7 8 | try {
Class rmClass = Assemble3D. class .getClassLoader().loadClass( "org.jdesktop.swinghelper.debug.CheckThreadViolationRepaintManager" );
RepaintManager.setCurrentManager((RepaintManager)rmClass.getConstructor().newInstance());
System.err.println( "EDT Debug Mode Is Active" );
}
catch (ClassNotFoundException e) {
}
|
This code tries to load a class, via reflection, that catches EDT violations (painting Swing components from the wrong thread) and that I only use during development to aid in debugging. I load the class via reflection so that when I distribute the application I can simply leave out the JAR file containing the debug class and everything will continue to work -- the class isn't found so an exception is thrown, caught and ignored and the application continues on. The problem with IcedTea is that when running as a Web Start application the call to
loadClass
in line 2 returns
null
instead of throwing a
ClassNotFoundException
. This means that the catch block isn't triggered and the exception is thrown all the way out of the main method, killing the application. It seems to only be a Web Start issue as running my development copy locally under IcedTea doesn't cause
loadClass
to return
null
. Of course this problem I can fix by changing the catch block to trap all exceptions, but the point is I shouldn't have to!
As I said at the beginning of this post I'm all for open-source software, but I believe there are cases where developers who give their time freely to projects should think more about the merits of the project and if it is really needed. The "official" Oracle release of Java is now, for all intense and purposes, under an open-source license for the development of desktop applications (mobile and embedded uses are a different kettle of fish). Given this, is there really any need for a clean room implementation, especially when that implementation is so buggy as to render it useless in many situations?