Documenting some work done to run JVM on a embedded product.
I found this worth noting down due to lack of information (or rather, largely scatter information in forum, blogsphere etc) around this topic. What can be found on internet are usually deployment on the ARMs. The main reference (with detail steps that's also applicable for MIPS) was:
Running OpenMUC on ARM systems
This project dealt with:
- Processor: MIPS 24Kc
- JVM: JamVM 1.5.4
- Classpath 0.98 (Could have been 0.99)
Here are the adapted steps, assuming the cross-compile tools are built and setup beforehand.
- zlib
CHOST=mips-example-linux-gnu ./configure
Before make, edit the Makefile to add -fPIC to the SFLAGS that's used to build the static lib. Otherwise will encounter error when building JamVM.
vim Makefile
SFLAGS=-O3 -fPIC -D_LARGEFILE64_SOURCE=1 -DHAVE_HIDDEN
make
Install the lib and headers to the toolchains directory:
sudo cp libz.a [toolchains_path]/lib
sudo cp zlib.h [toolchains_path]/include
sudo cp zconf.h [toolchains_path]/include
- JamVM
vim configure
mips-*-linux*) host_cpu=mips host_os=linux ;;
Configure and build:
./configure --host=mips-example-linux-gnu --with-classpath-install-dir=/usr/local --prefix=/usr/local --enable-shared --enable-int-threading --enable-int-direct --enable-int-caching --enable-int-prefetch --enable-runtime-reloc-checks --enable-tls --enable-dependency-tracking
make
I think the -install-dir and -prefix is whatever will be like at the target system. Here I just follow convention.
This is what will be printed when running "jamvm -version" on target later on.
Boot Library Path: /usr/local/lib/classpath
Boot Class Path: /usr/local/share/jamvm/classes.zip:/usr/local/share/classpath/glibj.zip
Strip down the binary (I think this step can be skipped if the target build will strip it when making the rootfs):
cd src
mips-example-linux-gnu-strip jamvm
Deploy to target at:
- src/jamvm -> /usr/sbin/jamvm
- lib/classes.zip -> /usr/local/share/jamvm/
- Classpath
Configure and build:
./configure --host=mips-example-linux-gnu --without-x --disable-gtk-peer --disable-plugin --disable-dssi --enable-jni --disable-gconf-peer --enable-default-preferences-peer=memory --enable-default-toolkit --disable-examples --disable-tools --disable-Werror --disable-alsa
make
The resulted lib/glibj.zip is ~9MB.
This can be reduced further. Unzip the glibj.zip, remove "unneeded" (for now) class and zip back.
Depends on the apps to run, some cannot be removed.
For example, these classes can be removed:
- gnu/CORBA
- gnu/java/awt
- gnu/javax/imageio
- gnu/javax/sound
- gnu/javax/swing
- java/sql/
- javax/imageio
- javax/sound
- javax/sql
- javax/swing
Zip the reduced classpath. This is reduced to about 6.5MB.
zip glibj.zip -r *
Deploy to target:
- lib/glibj.zip -> /usr/local/share/classpath/glibj.zip
All the native libraries must also be deployed on target:
find ./native/ -name "*.so" -exec cp {} ${ROOT_PATH}/usr/local/lib/classpath \;
After completed the above step, should be able to just run the java apps by:
jamvm -jar hello.jar