- Blog -

(A cheesy homepage for Justin Collins)
The Light at the End of a Tunnel Sorta

So I mentioned the shared whiteboard thing previously. I have been facing some serious headaches over one of the projects in particular. I don’t want to mention the name, but it’s been a real pain.

Why has it been such a problem? Well, let us see…first of all, it is not just one project, but two: a modified Java KVM and a modified J2ME compiler, two separate projects by two different people. I was able to track down the modified KVM code, which has been both a good and a horrible thing (horrible because it’s lead me down twisty paths I would not have known existed otherwise). However, I do not have the source for the modified compiler. This means that, while I can peer into the inner workings of the KVM and even poke around a bit, I cannot recompile the entire thing. This means no adding libraries or features not already present, because if I write it in C, the (modified) compiler may not compile them and if I do it in Java the KVM may not run it.

However, I am getting ahead of myself. What was the beginning of the issue? Quite simply, I needed to write an application with a GUI. Didn’t seem like a problem. But it is, because the project I need to use underneath is an extension of J2ME, and not the fancy MIDP version, but the tiny, teensy weensy CLDC version. That means no GUI.

BUT! I was in luck, because the person who extended the KVM (Kilobyte Virtual Machine…the J2ME VM from Sun) provided a nice little IPC interface to use with external programs. Cool! Oh, wait…the API is in C?? Why?? (Note: Probably because after working to an extend a virtual machine written in C, writing some shared memory IPC stuff was likely a cinch.) Java would have been so much more convenient…

But, wait again. I don’t need to write the GUI in C, though. Doesn’t Ruby have nice C bindings? Reads up on those… Yes, cool. Oh, wait, there’s a neato thing called SWIG which will even do most of the work for me? Neat! So I spent a while getting that all working, including writing wrapper methods (in C) and everything. I got to the point where Ruby would load the C libraries and even run them. But then I hit more trouble.

Most of the library is nice low-level handling of semaphores. And it was not working properly. I believe I traced this to the shared memory not being written correctly, thus giving me bogus semaphore IDs. However…I can’t change that part. I was able to mess around with the IPC code, because it was thankfully separate from the rest of the VM (that is, the API was). But it’s no good if the VM itself needs changed.

So I finally gave up. On the IPC stuff anyways. I looked at what I had available and decided, no matter how ridiculous it is, it’s better to be ridiculous than not working at all.

Before I explain the silliness I ended up with this evening, let me explain a bit how these VMs work. You do not simply run programs on them. Oh, no. First you start the VM (including setting up a virtual network topology), then you can either ‘inject’ applications into the system, or register services at particular VMs, which the applications can visit.

Also, the only kind of I/O really available in the limited world of J2ME is printing out to stdin and stderr. That’s pretty much it (in this implementation). I couldn’t open sockets, read files, or anything. At least, I couldn’t figure out how to.

So, what did I do? Well, something like this: I have a GUI written in Ruby and Tk, which will launch the VM and attach a file handle to the stdout of the VM. It then registers a ‘Whiteboard’ service, which will receive messages from other VMs regarding what’s happening on the remote whiteboards. So far, so good. Now, if the VM wishes to communicate to the GUI, it can do so by simply using a System.out.println(). Good enough, Ruby makes it easy to parse and deal with such things. But what about from the GUI to the VM? Well…what it does is ‘inject’ an application into the system, passing any information it needs to as command line arguments. Yes. That is right. Command line arguments for IPC.

Amazingly…it works. It’s going to take a little more tweaking, but I now have more to show for approximately two hours of work than the past days I’ve spent fighting with C APIs and semaphores and accessing shared memory and digging through J2ME documentation for hope.


UI in Java and Ruby

For my research, I need to implement a shared whiteboard, which is a fairly common example of collaborative software. I’m doing it with three different projects handling the communication side of it. Since two of these can be directly tied in with Java, it made since to start with a Java UI. The third, for some inexplicable reason, chose to implement IPC through a C interface. So, for that one, I’ll be writing the UI using Ruby.

I have completed a basic prototype for both, which just implements the ‘drawing’ part of the whiteboard. They have exactly the same amount of functionality (draw lines, save the history) and do it basically the same way (start line on mouse click, save points and draw as the mouse moves). I didn’t try to make these as short as possible, just as equivalent as possible.

The Java version, using AWT, is 95 lines long. The Ruby version, using Tk, is 50 lines long. Not too big of a difference, considering how short they are.

However…each line in Java seems quite a bit longer than the Ruby version. What if we compare based on the number of characters, rather than the number of lines? Hmmmm…the Java version comes out with 2831 characters, while the Ruby version only has 978! That is a lot less typing! (A third, basically).

Oh, well. Sigh…

Edit: Oops, I forgot I also wrote a convenience class for the Java version that stored the history. But it wasn’t really necessary and I did not do so in the Ruby version, so the comparison above is still accurate, I think.