|CONTENTS | PREV | NEXT||Java Remote Method Invocation|
Call and return data in RMI calls are formatted using the Java Object Serialization protocol. Each method invocation's CallData is represented by the ObjectIdentifier (the target of the call), an Operation (a number representing the method to be invoked), a Hash (a number that verifies that client stub and remote object skeleton use the same stub protocol), followed by a list of zero or more Arguments for the call.
In the JDK1.1 stub protocol the Operation represented the method number as assigned by rmic and the Hash was the stub/skeleton hash which is the stub's interface hash. In the JDK1.2 stub protocol (JDK1.2 stubs are generated using the -v1.2 option with rmic), Operation has the value -1 and the Hash is a hash representing the method to call. The hash is described in the section "The RemoteRef Interface:.
CallData: ObjectIdentifier Operation Hash Argumentsopt
ObjectIdentifier: ObjectNumber UniqueIdentifier
UniqueIdentifier: Number Time Count
Arguments: Value Arguments Value
Value: Object Primitive
A ReturnValue of an RMI call consists of a return code to indicate either a normal or exceptional return, a UniqueIdentifier to tag the return value (used to send a DGCAck if necessary) followed by the return result: either the Value returned or the Exception thrown.
ReturnValue: 0x01 UniqueIdentifier Valueopt 0x02 UniqueIdentifier Exception
Note - ObjectIdentifier, UniqueIdentifier, and EndpointIdentifier are not written out using default serialization, but each uses its own special write method (this is not the writeObject method used by Object Serialization); the write method for each type of identifier adds its component data consecutively to the output stream.
RMI overrides the
resolveClassmethods of ObjectOutputStream and ObjectInputStream respectively. Each class is annotated with the codebase URL (the location from which the class can be loaded). In the
annotateClassmethod, the classloader that loaded the class is queried for its codebase URL. If the classloader is non-null and the classloader has a non-null codebase, then the codebase is written to the stream using the
ObjectOutputStream.writeObjectmethod; otherwise a null is written to the stream using the
writeObjectmethod. Note: as an optimization, classes in the "java" package are not annotated, since they are always available to the receiver.
The class annotation is resolved during deserialization using the
resolveClassmethod first reads the annotation via the
ObjectInputStream.readObjectmethod. If the annotation, a codebase URL, is non-null, then it obtains the classloader for that URL and attempts to load the class. The class is loaded by using a java.net.URLConnection to fetch the class bytes (the same mechanism used by a web browser's applet classloader).