UnicastRemoteCall.java [plain text]
package gnu.java.rmi.server;
import java.io.DataInputStream;
import java.io.DataOutputStream;
import java.io.IOException;
import java.io.ObjectInput;
import java.io.ObjectOutput;
import java.io.StreamCorruptedException;
import java.rmi.RemoteException;
import java.rmi.MarshalException;
import java.rmi.UnmarshalException;
import java.rmi.server.RemoteCall;
import java.rmi.server.ObjID;
import java.rmi.server.UID;
import java.util.Vector;
public class UnicastRemoteCall
implements RemoteCall, ProtocolConstants
{
private UnicastConnection conn;
private Object result;
private Object object;
private int opnum;
private long hash;
private Vector vec;
private int ptr;
private ObjID objid;
private ObjectOutput oout;
private ObjectInput oin;
UnicastRemoteCall(UnicastConnection conn)
{
this.conn = conn;
}
UnicastRemoteCall(UnicastConnection conn, ObjID objid, int opnum, long hash)
throws RemoteException
{
this.conn = conn;
this.opnum = opnum;
this.hash = hash;
this.objid = objid;
}
UnicastConnection getConnection()
{
return conn;
}
public ObjectOutput getOutputStream() throws IOException
{
if (vec == null)
vec = new Vector();
return (new DummyObjectOutputStream());
}
public void releaseOutputStream() throws IOException
{
if (vec != null)
{
oout = conn.getObjectOutputStream();
for (int i = 0; i < vec.size(); i += 2)
{
boolean primitive = ((Boolean)vec.elementAt(i)).booleanValue();
Object data = vec.elementAt(i+1);
if (!primitive)
oout.writeObject(data);
else
{
if (data instanceof Boolean)
oout.writeBoolean(((Boolean)data).booleanValue());
else if (data instanceof Character)
oout.writeChar(((Character)data).charValue());
else if (data instanceof Byte)
oout.writeByte(((Byte)data).byteValue());
else if (data instanceof Short)
oout.writeShort(((Short)data).shortValue());
else if (data instanceof Integer)
oout.writeInt(((Integer)data).intValue());
else if (data instanceof Long)
oout.writeLong(((Long)data).longValue());
}
}
vec = null;
}
if(oout != null)
oout.flush();
}
public ObjectInput startInputStream() throws IOException
{
if (conn != null) {
return (oin = conn.startObjectInputStream());
} else {
return getInputStream(); }
}
public ObjectInput getInputStream() throws IOException
{
if (conn != null)
{
if(oin == null)
return (oin = conn.getObjectInputStream());
else
return oin;
}
else
{
ptr = 0;
return (new DummyObjectInputStream());
}
}
public void releaseInputStream() throws IOException
{
}
public ObjectOutput getResultStream(boolean success)
throws IOException, StreamCorruptedException
{
vec = new Vector();
return new DummyObjectOutputStream();
}
public void executeCall() throws Exception
{
byte returncode;
ObjectInput oin;
try
{
DataOutputStream dout = conn.getDataOutputStream();
dout.write(MESSAGE_CALL);
oout = conn.startObjectOutputStream(); objid.write(oout);
oout.writeInt(opnum);
oout.writeLong(hash);
}
catch(IOException ex)
{
throw new MarshalException("Try to write header but failed.", ex);
}
try
{
releaseOutputStream();
DataInputStream din = conn.getDataInputStream();
if (din.readByte() != MESSAGE_CALL_ACK)
throw new RemoteException("Call not acked");
oin = startInputStream();
returncode = oin.readByte();
UID.read(oin);
}
catch(IOException ex)
{
throw new UnmarshalException("Try to read header but failed:", ex);
}
switch(returncode)
{
case RETURN_ACK: return;
case RETURN_NACK:
Object returnobj;
try
{
returnobj = oin.readObject();
}
catch(Exception ex2)
{
throw new UnmarshalException
("Try to read exception object but failed", ex2);
}
if(!(returnobj instanceof Exception))
throw new UnmarshalException("Should be Exception type here: "
+ returnobj);
throw (Exception)returnobj;
default:
throw new UnmarshalException("Invalid return code");
}
}
public void done() throws IOException
{
}
boolean isReturnValue()
{
return vec.size() > 0;
}
Object returnValue()
{
return vec.elementAt(1);
}
Object[] getArguments()
{
return vec.toArray();
}
Object getObject()
{
return object;
}
int getOpnum()
{
return opnum;
}
long getHash()
{
return hash;
}
void setReturnValue(Object obj)
{
vec.removeAllElements();
vec.addElement(obj);
}
private class DummyObjectOutputStream implements ObjectOutput
{
DummyObjectOutputStream()
{
}
public void writeBoolean(boolean v) throws IOException
{
vec.addElement(Boolean.TRUE);
vec.addElement(Boolean.valueOf(v));
}
public void writeByte(int v) throws IOException
{
vec.addElement(Boolean.TRUE);
vec.addElement(new Byte((byte) v));
}
public void writeChar(int v) throws IOException
{
vec.addElement(Boolean.TRUE);
vec.addElement(new Character((char) v));
}
public void writeDouble(double v) throws IOException
{
vec.addElement(Boolean.TRUE);
vec.addElement(new Double(v));
}
public void writeFloat(float v) throws IOException
{
vec.addElement(Boolean.TRUE);
vec.addElement(new Float(v));
}
public void writeInt(int v) throws IOException
{
vec.addElement(Boolean.TRUE);
vec.addElement(new Integer(v));
}
public void writeLong(long v) throws IOException
{
vec.addElement(Boolean.TRUE);
vec.addElement(new Long(v));
}
public void writeShort(int v) throws IOException
{
vec.addElement(Boolean.TRUE);
vec.addElement(new Short((short) v));
}
public void writeObject(Object obj) throws IOException
{
vec.addElement(Boolean.FALSE);
vec.addElement(obj);
}
public void write(byte b[]) throws IOException
{
throw new IOException("not required");
}
public void write(byte b[], int off, int len) throws IOException
{
throw new IOException("not required");
}
public void write(int b) throws IOException
{
throw new IOException("not required");
}
public void writeBytes(String s) throws IOException
{
throw new IOException("not required");
}
public void writeChars(String s) throws IOException
{
throw new IOException("not required");
}
public void writeUTF(String str) throws IOException
{
throw new IOException("not required");
}
public void flush() throws IOException
{
}
public void close() throws IOException
{
}
}
private class DummyObjectInputStream implements ObjectInput
{
DummyObjectInputStream()
{
}
public boolean readBoolean() throws IOException
{
Object obj = vec.elementAt(ptr++);
return ((Boolean) obj).booleanValue();
}
public byte readByte() throws IOException
{
Object obj = vec.elementAt(ptr++);
return ((Byte) obj).byteValue();
}
public char readChar() throws IOException
{
Object obj = vec.elementAt(ptr++);
return ((Character) obj).charValue();
}
public double readDouble() throws IOException
{
Object obj = vec.elementAt(ptr++);
return ((Double) obj).doubleValue();
}
public float readFloat() throws IOException
{
Object obj = vec.elementAt(ptr++);
return ((Float) obj).floatValue();
}
public int readInt() throws IOException
{
Object obj = vec.elementAt(ptr++);
return ((Integer) obj).intValue();
}
public long readLong() throws IOException
{
Object obj = vec.elementAt(ptr++);
return ((Long) obj).longValue();
}
public short readShort() throws IOException
{
Object obj = vec.elementAt(ptr++);
return ((Short) obj).shortValue();
}
public Object readObject() throws IOException
{
return vec.elementAt(ptr++);
}
public int read(byte b[]) throws IOException
{
throw new IOException("not required");
}
public int read(byte b[], int off, int len) throws IOException
{
throw new IOException("not required");
}
public int read() throws IOException
{
throw new IOException("not required");
}
public long skip(long n) throws IOException
{
throw new IOException("not required");
}
public int available() throws IOException
{
throw new IOException("not required");
}
public void readFully(byte b[]) throws IOException
{
throw new IOException("not required");
}
public void readFully(byte b[], int off, int len) throws IOException
{
throw new IOException("not required");
}
public String readLine() throws IOException
{
throw new IOException("not required");
}
public String readUTF() throws IOException
{
throw new IOException("not required");
}
public int readUnsignedByte() throws IOException
{
throw new IOException("not required");
}
public int readUnsignedShort() throws IOException
{
throw new IOException("not required");
}
public int skipBytes(int n) throws IOException
{
throw new IOException("not required");
}
public void close() throws IOException
{
}
}
}