Theory of Operation
The foundation of the interaction between the Java VM and Smalltalk is Java Native Interface (JNI). It allows invoking Java functionality from native code. It has originally been designed to allow interaction with the programming language C/C++. For each Java class a Smalltalk wrapper/proxy class is automatically generated. This wrapper class translates Smalltalk method invocations into JNI calls. See http://java.sun.com/javase/6/docs/technotes/guides/jni/ for a detailed description of JNI.
In Java garbage collection takes care of memory management. In order to determine if an object is no longer “in use” and therefore can be deallocated, the Java VM checks if an object has incoming references. When invoking a native method from Java the VM automatically manages these references by tracking the objects created in the scope of the call. When using JNI from Smalltalk there are no such “natural” method invocation boundaries, so you have to mark these boundaries according to your application logic by calling special methods. A description of the concept of local/global references can be found at http://java.sun.com/javase/6/docs/technotes/guides/jni/spec/design.html#wp16785.
| vm player | vm := JavaVM getCurrent. vm pushLocalFrame: 16. "Mark beginning of reference tracking and ensure space for at least 16 references" player := Com_apisgroup_media_audio_MP3AudioPlayer getInstance: (JString fromString: 'foo.mp3'). "Create a audio player instance" player playInBackground. "Create a Java thread and play audio file in background" vm popLocalFrame. "Mark end of reference tracking and delete all references created in this scope"