Pet Bugs II - Debugger War Stories
AlphaHelix queries: "A few weeks back there was an article on Pet Bugs, where people were asked about their favorite bugs. I have a different sort of question: what was your greatest debugging challenge? I've been debugging for a long time, from analog circuits all the way up to multi-kLOC multithreaded servers, and I have some pretty grisly war stories, like the time I debugged a problem in a third-party DLL in machine code because the client didn't have the source for it (yay open source.) What was your greatest debugging triumph?" The first time Slashdot did this it was more about bugs that you had encountered (and may not have solved), this one is about bugs in your own projects code and the trials and tribulations you had to go thru to get them fixed.
The really sad part here is that certain types of people rail on C and C++ for having pointers, and consequently being susceptible to null-pointer bugs, comparing at the wrong level of indirection, etc, and yet here is an equally subtle and unfortunate situation in Java, a language much hyped for its improved safety.
I can see a good reason for low-level languages to provide this level of control, and the consequent risks associated with it. Surely, though, it would be better for most applications if higher level languages prevented such things happening at compile-time, rather than leaving you to clean up the mess in debugging (assuming, of course, that you actually hit the code in question during your testing). Until then, threads like this will forever feature bugs that should never be able to happen...
If you disagree, post your argument. (-1, Overrated) isn't your personal censorship tool for views you don't like.
Reflection is a nice feature in Java except they made it a pain in the ass to use. I work on a product that is a Java application running on Windows, Linux, Solaris, and Mac (both OSX and Mac OS 9). Because we are still supporting Mac OS 9, we cannot use a Java 2 compiler at all- so we are squeezing the entire tree through Sun's 1.1.8 compiler every night. (So we're still writing Java 1.1 code! In this day and age! If you call any Java 2 method, like add() on a Vector, it breaks the nightly build.)
Now there are some things that our customers want that absolutely require Java 2, like drag and drop. If you are running Mac OS 9, drag and drop won't work in our program. Sorry. But we have it working for everybody else on all other platforms- by using reflection to access the DnD classes! And the code looks horrible. One line of ordinary code balloons to five lines of incomprehensible gibberish when you use reflection.
The way I see it there are two primary uses for reflection. One is the use that Sun originally intended- for people writing IDEs, bean containers, debuggers, profilers, etc. The other is for people like us, who are compiling against a fossilized version of the JDK but need to introduce some forward-compatibility and access classes we know are usually there but we can't compile against statically. Sun's attitude is always to tell all customers to upgrade to their latest and greatest version of Java. (Sun's inability to take on the backward-compatibility issue from either a design or a policy perspective is really annoying. It's what killed the whole applet idea. And now their JDK 1.4 compiler is spitting out classes with version numbers that make old software freak out. I still have to find the compiler switch that turns that off.)
I think it would be cool if Java had a "reflection" keyword with which you could declare a block of code as being dynamically and not statically compiled- so you could write ordinary code in there and the compiler would break it down during a preprocessing step into the required Class/Method/Field gibberish and let you catch something like an "UnsupportedApiException" in a catch block underneath. Of course, the chance of that happening is zero, and even if it did happen, the 1.1.8 compiler wouldn't understand it anyway. Does anyone know if Sun has any plans for introducing a standard for compiler extensions? It strikes me as a move that would involve relinquishing too much control.