Re-revamp. I may re-re-revamp later to eliminate the reflection based streaming
altogether as that also solves the "Class.getDeclaredFields() is not required to return fields in declaration order" problem which has been looming. However, this should work for now. git-svn-id: svn+ssh://src.earth.threerings.net/narya/trunk@4701 542714f4-19e9-0310-aa3c-eee0fc999fb1
This commit is contained in:
@@ -92,7 +92,10 @@
|
||||
<!-- now instrument the associated files -->
|
||||
<instream outdir="${classes.dir}">
|
||||
<path refid="classpath"/>
|
||||
<fileset dir="${classes.dir}" includes="**/*.class"/>
|
||||
<fileset dir="${classes.dir}" includes="**/data/*.class"/>
|
||||
<fileset dir="${classes.dir}" includes="**/net/*.class"/>
|
||||
<fileset dir="${classes.dir}" includes="**/dobj/*.class"/>
|
||||
<fileset dir="${classes.dir}" includes="**/util/*.class"/>
|
||||
</instream>
|
||||
</target>
|
||||
|
||||
|
||||
@@ -29,8 +29,8 @@ import java.util.List;
|
||||
import java.util.RandomAccess;
|
||||
|
||||
/**
|
||||
* Code to read and write basic object types (like arrays of primitives,
|
||||
* {@link Integer} instances, {@link Double} instances, etc.).
|
||||
* Code to read and write basic object types (like arrays of primitives, {@link Integer} instances,
|
||||
* {@link Double} instances, etc.).
|
||||
*/
|
||||
public class BasicStreamers
|
||||
{
|
||||
@@ -83,7 +83,7 @@ public class BasicStreamers
|
||||
};
|
||||
|
||||
/** Streams {@link Boolean} instances. */
|
||||
public static class BooleanStreamer extends Streamer
|
||||
public static class BooleanStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
@@ -98,17 +98,10 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeBoolean(((Boolean)object).booleanValue());
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
// nothing to do here
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link Byte} instances. */
|
||||
public static class ByteStreamer extends Streamer
|
||||
public static class ByteStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
@@ -123,17 +116,10 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeByte(((Byte)object).byteValue());
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
// nothing to do here
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link Short} instances. */
|
||||
public static class ShortStreamer extends Streamer
|
||||
public static class ShortStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
@@ -148,17 +134,10 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeShort(((Short)object).shortValue());
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
// nothing to do here
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link Character} instances. */
|
||||
public static class CharacterStreamer extends Streamer
|
||||
public static class CharacterStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)throws IOException
|
||||
@@ -172,17 +151,10 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeChar(((Character)object).charValue());
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
// nothing to do here
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link Integer} instances. */
|
||||
public static class IntegerStreamer extends Streamer
|
||||
public static class IntegerStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
@@ -197,17 +169,10 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeInt(((Integer)object).intValue());
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
// nothing to do here
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link Long} instances. */
|
||||
public static class LongStreamer extends Streamer
|
||||
public static class LongStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
@@ -222,17 +187,10 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeLong(((Long)object).longValue());
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
// nothing to do here
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link Float} instances. */
|
||||
public static class FloatStreamer extends Streamer
|
||||
public static class FloatStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
@@ -247,17 +205,10 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeFloat(((Float)object).floatValue());
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
// nothing to do here
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link Double} instances. */
|
||||
public static class DoubleStreamer extends Streamer
|
||||
public static class DoubleStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
@@ -272,17 +223,10 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeDouble(((Double)object).doubleValue());
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
// nothing to do here
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link String} instances. */
|
||||
public static class StringStreamer extends Streamer
|
||||
public static class StringStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
@@ -297,8 +241,191 @@ public class BasicStreamers
|
||||
{
|
||||
out.writeUTF((String)object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of booleans. */
|
||||
public static class BooleanArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return readBooleanArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeBooleanArray(out, (boolean[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of bytes. */
|
||||
public static class ByteArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return readByteArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeByteArray(out, (byte[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of shorts. */
|
||||
public static class ShortArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return readShortArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeShortArray(out, (short[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of chars. */
|
||||
public static class CharArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return readCharArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeCharArray(out, (char[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of ints. */
|
||||
public static class IntArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return readIntArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeIntArray(out, (int[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of longs. */
|
||||
public static class LongArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return readLongArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeLongArray(out, (long[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of floats. */
|
||||
public static class FloatArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return readFloatArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeFloatArray(out, (float[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of doubles. */
|
||||
public static class DoubleArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return readDoubleArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeDoubleArray(out, (double[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of Object instances. */
|
||||
public static class ObjectArrayStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
return readObjectArray(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeObjectArray(out, (Object[])object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link List} instances. */
|
||||
public static class ListStreamer extends BasicStreamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
return readList(in);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
writeList(out, (List)object);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link String} instances. */
|
||||
public static class BasicStreamer extends Streamer
|
||||
{
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
@@ -306,21 +433,124 @@ public class BasicStreamers
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of booleans. */
|
||||
public static class BooleanArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static boolean[] readBooleanArray (ObjectInputStream ins)
|
||||
throws IOException
|
||||
{
|
||||
return new boolean[in.readInt()];
|
||||
boolean[] value = new boolean[ins.readInt()];
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = ins.readBoolean();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
public static byte[] readByteArray (ObjectInputStream ins)
|
||||
throws IOException
|
||||
{
|
||||
byte[] value = new byte[ins.readInt()];
|
||||
int remain = value.length, offset = 0, read;
|
||||
while (remain > 0) {
|
||||
if ((read = ins.read(value, offset, remain)) > 0) {
|
||||
remain -= read;
|
||||
offset += read;
|
||||
} else {
|
||||
throw new EOFException();
|
||||
}
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static short[] readShortArray (ObjectInputStream ins)
|
||||
throws IOException
|
||||
{
|
||||
short[] value = new short[ins.readInt()];
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = ins.readShort();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static char[] readCharArray (ObjectInputStream ins)
|
||||
throws IOException
|
||||
{
|
||||
char[] value = new char[ins.readInt()];
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = ins.readChar();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static int[] readIntArray (ObjectInputStream ins)
|
||||
throws IOException
|
||||
{
|
||||
int[] value = new int[ins.readInt()];
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = ins.readInt();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static long[] readLongArray (ObjectInputStream ins)
|
||||
throws IOException
|
||||
{
|
||||
long[] value = new long[ins.readInt()];
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = ins.readLong();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static float[] readFloatArray (ObjectInputStream ins)
|
||||
throws IOException
|
||||
{
|
||||
float[] value = new float[ins.readInt()];
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = ins.readFloat();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static double[] readDoubleArray (ObjectInputStream ins)
|
||||
throws IOException
|
||||
{
|
||||
double[] value = new double[ins.readInt()];
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = ins.readDouble();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static Object[] readObjectArray (ObjectInputStream ins)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
Object[] value = new Object[ins.readInt()];
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = ins.readObject();
|
||||
}
|
||||
return value;
|
||||
}
|
||||
|
||||
public static ArrayList readList (ObjectInputStream ins)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
int ecount = ins.readInt();
|
||||
ArrayList<Object> list = new ArrayList<Object>(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
list.add(ins.readObject());
|
||||
}
|
||||
return list;
|
||||
}
|
||||
|
||||
public static void writeBooleanArray (ObjectOutputStream out, boolean[] value)
|
||||
throws IOException
|
||||
{
|
||||
boolean[] value = (boolean[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
@@ -328,104 +558,17 @@ public class BasicStreamers
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
boolean[] value = (boolean[])object;
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = in.readBoolean();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of bytes. */
|
||||
public static class ByteArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static void writeByteArray (ObjectOutputStream out, byte[] value)
|
||||
throws IOException
|
||||
{
|
||||
return new byte[in.readInt()];
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
byte[] value = (byte[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
out.write(value);
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
byte[] value = (byte[])object;
|
||||
int remain = value.length, offset = 0, read;
|
||||
while (remain > 0) {
|
||||
if ((read = in.read(value, offset, remain)) > 0) {
|
||||
remain -= read;
|
||||
offset += read;
|
||||
} else {
|
||||
throw new EOFException();
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of shorts. */
|
||||
public static class ShortArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static void writeCharArray (ObjectOutputStream out, char[] value)
|
||||
throws IOException
|
||||
{
|
||||
return new short[in.readInt()];
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
short[] value = (short[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
out.writeShort(value[ii]);
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
short[] value = (short[])object;
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = in.readShort();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of chars. */
|
||||
public static class CharArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
{
|
||||
return new char[in.readInt()];
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
char[] value = (char[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
@@ -433,33 +576,19 @@ public class BasicStreamers
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
public static void writeShortArray (ObjectOutputStream out, short[] value)
|
||||
throws IOException
|
||||
{
|
||||
char[] value = (char[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = in.readChar();
|
||||
}
|
||||
out.writeShort(value[ii]);
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of ints. */
|
||||
public static class IntArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static void writeIntArray (ObjectOutputStream out, int[] value)
|
||||
throws IOException
|
||||
{
|
||||
return new int[in.readInt()];
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
int[] value = (int[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
@@ -467,33 +596,9 @@ public class BasicStreamers
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
int[] value = (int[])object;
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = in.readInt();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of longs. */
|
||||
public static class LongArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static void writeLongArray (ObjectOutputStream out, long[] value)
|
||||
throws IOException
|
||||
{
|
||||
return new long[in.readInt()];
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
long[] value = (long[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
@@ -501,33 +606,9 @@ public class BasicStreamers
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
long[] value = (long[])object;
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = in.readLong();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of floats. */
|
||||
public static class FloatArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static void writeFloatArray (ObjectOutputStream out, float[] value)
|
||||
throws IOException
|
||||
{
|
||||
return new float[in.readInt()];
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
float[] value = (float[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
@@ -535,33 +616,9 @@ public class BasicStreamers
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
float[] value = (float[])object;
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = in.readFloat();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of doubles. */
|
||||
public static class DoubleArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static void writeDoubleArray (ObjectOutputStream out, double[] value)
|
||||
throws IOException
|
||||
{
|
||||
return new double[in.readInt()];
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
double[] value = (double[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
@@ -569,33 +626,9 @@ public class BasicStreamers
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
double[] value = (double[])object;
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = in.readDouble();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams arrays of Object instances. */
|
||||
public static class ObjectArrayStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static void writeObjectArray (ObjectOutputStream out, Object[] value)
|
||||
throws IOException
|
||||
{
|
||||
return new Object[in.readInt()];
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
Object[] value = (Object[])object;
|
||||
int ecount = value.length;
|
||||
out.writeInt(ecount);
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
@@ -603,63 +636,21 @@ public class BasicStreamers
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
Object[] value = (Object[])object;
|
||||
int ecount = value.length;
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value[ii] = in.readObject();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/** Streams {@link List} instances. */
|
||||
public static class ListStreamer extends Streamer
|
||||
{
|
||||
// documentation inherited
|
||||
public Object createObject (ObjectInputStream in)
|
||||
public static void writeList (ObjectOutputStream out, List value)
|
||||
throws IOException
|
||||
{
|
||||
return new ArrayList(0); // minimally sized
|
||||
// (We thought about using a ThreadLocal to assist here... we could read the length of
|
||||
// the list here and construct the ArrayList with the right size, and then read the
|
||||
// length out of the ThreadLocal down in readObject(). Instead, we simply create a
|
||||
// 0-length list here, which generates minimal garbage when we ensureCapacity() down in
|
||||
// readObject.)
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void writeObject (Object object, ObjectOutputStream out, boolean useWriter)
|
||||
throws IOException
|
||||
{
|
||||
List list = (List)object;
|
||||
int ecount = list.size();
|
||||
int ecount = value.size();
|
||||
out.writeInt(ecount);
|
||||
if (list instanceof RandomAccess) {
|
||||
if (value instanceof RandomAccess) {
|
||||
// if RandomAccess, it's faster and less garbagey this way
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
out.writeObject(list.get(ii));
|
||||
out.writeObject(value.get(ii));
|
||||
}
|
||||
} else {
|
||||
// if not RandomAccess, go ahead and make an Iterator...
|
||||
for (Object o : list) {
|
||||
for (Object o : value) {
|
||||
out.writeObject(o);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// documentation inherited
|
||||
public void readObject (Object object, ObjectInputStream in, boolean useReader)
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
@SuppressWarnings("unchecked") ArrayList<Object> value = (ArrayList<Object>)object;
|
||||
int ecount = in.readInt();
|
||||
value.ensureCapacity(ecount); // resize the array once
|
||||
for (int ii = 0; ii < ecount; ii++) {
|
||||
value.add(in.readObject());
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -57,24 +57,24 @@ public abstract class FieldMarshaller
|
||||
createMarshallers();
|
||||
}
|
||||
|
||||
// // first look to see if this field has custom reader/writer methods
|
||||
// Method reader = null, writer = null;
|
||||
// try {
|
||||
// reader = field.getDeclaringClass().getMethod(
|
||||
// getReaderMethodName(field.getName()), READER_ARGS);
|
||||
// writer = field.getDeclaringClass().getMethod(
|
||||
// getWriterMethodName(field.getName()), WRITER_ARGS);
|
||||
// return new MethodFieldMarshaller(reader, writer);
|
||||
// } catch (NoSuchMethodException nsme) {
|
||||
// // no problem
|
||||
// }
|
||||
// if ((reader != null || writer != null) && (reader == null || writer == null)) {
|
||||
// log.warning("Class contains one but not both custom field reader and writer " +
|
||||
// "[class=" + field.getDeclaringClass().getName() +
|
||||
// ", field=" + field.getName() + ", reader=" + reader +
|
||||
// ", writer=" + writer + "].");
|
||||
// // fall through to using reflection on the fields...
|
||||
// }
|
||||
// first look to see if this field has custom reader/writer methods
|
||||
Method reader = null, writer = null;
|
||||
try {
|
||||
reader = field.getDeclaringClass().getMethod(
|
||||
getReaderMethodName(field.getName()), READER_ARGS);
|
||||
writer = field.getDeclaringClass().getMethod(
|
||||
getWriterMethodName(field.getName()), WRITER_ARGS);
|
||||
return new MethodFieldMarshaller(reader, writer);
|
||||
} catch (NoSuchMethodException nsme) {
|
||||
// no problem
|
||||
}
|
||||
if ((reader != null || writer != null) && (reader == null || writer == null)) {
|
||||
log.warning("Class contains one but not both custom field reader and writer " +
|
||||
"[class=" + field.getDeclaringClass().getName() +
|
||||
", field=" + field.getName() + ", reader=" + reader +
|
||||
", writer=" + writer + "].");
|
||||
// fall through to using reflection on the fields...
|
||||
}
|
||||
|
||||
Class ftype = field.getType();
|
||||
if (ftype.isInterface()) {
|
||||
|
||||
@@ -245,7 +245,7 @@ public class Streamer
|
||||
* array must be read before creating the array).
|
||||
*/
|
||||
public Object createObject (ObjectInputStream in)
|
||||
throws IOException
|
||||
throws IOException, ClassNotFoundException
|
||||
{
|
||||
try {
|
||||
// if our target class is an array type, read in the element count and create an array
|
||||
@@ -435,6 +435,18 @@ public class Streamer
|
||||
return;
|
||||
}
|
||||
|
||||
// look up the reader and writer methods
|
||||
try {
|
||||
_reader = target.getMethod(READER_METHOD_NAME, READER_ARGS);
|
||||
} catch (NoSuchMethodException nsme) {
|
||||
// nothing to worry about, we just don't have one
|
||||
}
|
||||
try {
|
||||
_writer = target.getMethod(WRITER_METHOD_NAME, WRITER_ARGS);
|
||||
} catch (NoSuchMethodException nsme) {
|
||||
// nothing to worry about, we just don't have one
|
||||
}
|
||||
|
||||
// reflect on all the object's fields
|
||||
_fields = ClassUtil.getFields(target);
|
||||
int fcount = _fields.length;
|
||||
@@ -448,18 +460,6 @@ public class Streamer
|
||||
_fields[ii].getName() + ".");
|
||||
}
|
||||
}
|
||||
|
||||
// look up the reader and writer methods
|
||||
try {
|
||||
_reader = target.getMethod(READER_METHOD_NAME, READER_ARGS);
|
||||
} catch (NoSuchMethodException nsme) {
|
||||
// nothing to worry about, we just don't have one
|
||||
}
|
||||
try {
|
||||
_writer = target.getMethod(WRITER_METHOD_NAME, WRITER_ARGS);
|
||||
} catch (NoSuchMethodException nsme) {
|
||||
// nothing to worry about, we just don't have one
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
|
||||
@@ -45,6 +45,7 @@ import org.apache.tools.ant.types.FileSet;
|
||||
import org.apache.tools.ant.types.Path;
|
||||
|
||||
import com.samskivert.io.StreamUtil;
|
||||
import com.threerings.io.BasicStreamers;
|
||||
import com.threerings.io.FieldMarshaller;
|
||||
import com.threerings.io.Streamable;
|
||||
|
||||
@@ -94,6 +95,13 @@ public class InstrumentStreamableTask extends Task
|
||||
}
|
||||
}
|
||||
|
||||
// instantiate streamable
|
||||
try {
|
||||
_streamable = _pool.get(Streamable.class.getName());
|
||||
} catch (Exception e) {
|
||||
throw new BuildException("Unable to load " + Streamable.class.getName() + ": " + e);
|
||||
}
|
||||
|
||||
// now process the files
|
||||
for (FileSet fs : _filesets) {
|
||||
DirectoryScanner ds = fs.getDirectoryScanner(getProject());
|
||||
@@ -122,7 +130,7 @@ public class InstrumentStreamableTask extends Task
|
||||
}
|
||||
|
||||
try {
|
||||
if (isStreamable(clazz)) {
|
||||
if (clazz.subtypeOf(_streamable)) {
|
||||
processStreamable(source, clazz);
|
||||
}
|
||||
} catch (NotFoundException nfe) {
|
||||
@@ -131,24 +139,6 @@ public class InstrumentStreamableTask extends Task
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* Returns true if the supplied class or any of its parents implements {@link Streamable}.
|
||||
*/
|
||||
protected boolean isStreamable (CtClass clazz)
|
||||
throws NotFoundException
|
||||
{
|
||||
if (clazz == null) {
|
||||
return false;
|
||||
}
|
||||
|
||||
for (CtClass iface : clazz.getInterfaces()) {
|
||||
if (iface.getName().equals(Streamable.class.getName())) {
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return isStreamable(clazz.getSuperclass());
|
||||
}
|
||||
|
||||
/**
|
||||
* Instruments the supplied {@link Streamable} implementing class.
|
||||
*/
|
||||
@@ -176,9 +166,10 @@ public class InstrumentStreamableTask extends Task
|
||||
if (!methods.contains(rname)) {
|
||||
String reader =
|
||||
"public void " + rname + " (com.threerings.io.ObjectInputStream ins) {\n" +
|
||||
" " + field.getName() + " = " + getFieldReader(field) + ";\n" +
|
||||
// " throws java.io.IOException, java.lang.ClassNotFoundException\n" +
|
||||
" " + getFieldReader(field) + "\n" +
|
||||
"}";
|
||||
// System.out.println("Adding reader " + clazz.getName() + "." + rname);
|
||||
// System.out.println("Adding reader " + clazz.getName() + ":\n" + reader);
|
||||
try {
|
||||
clazz.addMethod(CtNewMethod.make(reader, clazz));
|
||||
added++;
|
||||
@@ -191,11 +182,12 @@ public class InstrumentStreamableTask extends Task
|
||||
|
||||
String wname = FieldMarshaller.getWriterMethodName(field.getName());
|
||||
if (!methods.contains(wname)) {
|
||||
// System.out.println("Adding writer " + clazz.getName() + "." + wname);
|
||||
String writer =
|
||||
"public void " + wname + " (com.threerings.io.ObjectOutputStream out) {\n" +
|
||||
" out." + getFieldWriter(field) + ";\n" +
|
||||
// " throws java.io.IOException\n" +
|
||||
" " + getFieldWriter(field) + "\n" +
|
||||
"}";
|
||||
// System.out.println("Adding writer " + clazz.getName() + ":\n" + writer);
|
||||
try {
|
||||
clazz.addMethod(CtNewMethod.make(writer, clazz));
|
||||
added++;
|
||||
@@ -222,25 +214,47 @@ public class InstrumentStreamableTask extends Task
|
||||
throws NotFoundException
|
||||
{
|
||||
CtClass type = field.getType();
|
||||
String name = field.getName();
|
||||
if (type.getName().equals("java.lang.String")) {
|
||||
return "ins.readUTF()";
|
||||
return readWrap(field, name + " = ins.readUTF();");
|
||||
} else if (type.equals(CtClass.booleanType) || type.getName().equals("java.lang.Boolean")) {
|
||||
return "ins.readBoolean()";
|
||||
return readWrap(field, name + " = ins.readBoolean();");
|
||||
} else if (type.equals(CtClass.byteType) || type.getName().equals("java.lang.Byte")) {
|
||||
return "ins.readByte()";
|
||||
return readWrap(field, name + " = ins.readByte();");
|
||||
} else if (type.equals(CtClass.shortType) || type.getName().equals("java.lang.Short")) {
|
||||
return "ins.readShort()";
|
||||
return readWrap(field, name + " = ins.readShort();");
|
||||
} else if (type.equals(CtClass.intType) || type.getName().equals("java.lang.Integer")) {
|
||||
return "ins.readInt()";
|
||||
return readWrap(field, name + " = ins.readInt();");
|
||||
} else if (type.equals(CtClass.longType) || type.getName().equals("java.lang.Long")) {
|
||||
return "ins.readLong()";
|
||||
return readWrap(field, name + " = ins.readLong();");
|
||||
} else if (type.equals(CtClass.floatType) || type.getName().equals("java.lang.Float")) {
|
||||
return "ins.readFloat()";
|
||||
return readWrap(field, name + " = ins.readFloat();");
|
||||
} else if (type.equals(CtClass.doubleType) || type.getName().equals("java.lang.Double")) {
|
||||
return "ins.readDouble()";
|
||||
} else {
|
||||
return "(" + type.getName() + ")ins.readObject()";
|
||||
return readWrap(field, name + " = ins.readDouble();");
|
||||
}
|
||||
|
||||
if (type.isArray()) {
|
||||
CtClass ctype = type.getComponentType();
|
||||
if (ctype.equals(CtClass.booleanType)) {
|
||||
return readWrap(field, name + " = " + BSNAME + ".readBooleanArray(ins);");
|
||||
} else if (ctype.equals(CtClass.byteType)) {
|
||||
return readWrap(field, name + " = " + BSNAME + ".readByteArray(ins);");
|
||||
} else if (ctype.equals(CtClass.shortType)) {
|
||||
return readWrap(field, name + " = " + BSNAME + ".readShortArray(ins);");
|
||||
} else if (ctype.equals(CtClass.intType)) {
|
||||
return readWrap(field, name + " = " + BSNAME + ".readIntArray(ins);");
|
||||
} else if (ctype.equals(CtClass.longType)) {
|
||||
return readWrap(field, name + " = " + BSNAME + ".readLongArray(ins);");
|
||||
} else if (ctype.equals(CtClass.floatType)) {
|
||||
return readWrap(field, name + " = " + BSNAME + ".readFloat(ins);");
|
||||
} else if (ctype.equals(CtClass.doubleType)) {
|
||||
return readWrap(field, name + " = " + BSNAME + ".readDoubleArray(ins);");
|
||||
} else if (ctype.getName().equals("java.lang.Object")) {
|
||||
return readWrap(field, name + " = " + BSNAME + ".readObjectArray(ins);");
|
||||
}
|
||||
}
|
||||
|
||||
return readWrap(field, name + " = (" + type.getName() + ")ins.readObject();");
|
||||
}
|
||||
|
||||
protected String getFieldWriter (CtField field)
|
||||
@@ -248,24 +262,75 @@ public class InstrumentStreamableTask extends Task
|
||||
{
|
||||
CtClass type = field.getType();
|
||||
String name = field.getName();
|
||||
|
||||
if (type.equals(CtClass.booleanType) || type.getName().equals("java.lang.Boolean")) {
|
||||
return "writeBoolean(" + name + ")";
|
||||
return writeWrap(field, "out.writeBoolean(" + name + ");");
|
||||
} else if (type.equals(CtClass.byteType) || type.getName().equals("java.lang.Byte")) {
|
||||
return "writeByte(" + name + ")";
|
||||
return writeWrap(field, "out.writeByte(" + name + ");");
|
||||
} else if (type.equals(CtClass.shortType) || type.getName().equals("java.lang.Short")) {
|
||||
return "writeShort(" + name + ")";
|
||||
return writeWrap(field, "out.writeShort(" + name + ");");
|
||||
} else if (type.equals(CtClass.intType) || type.getName().equals("java.lang.Integer")) {
|
||||
return "writeInt(" + name + ")";
|
||||
return writeWrap(field, "out.writeInt(" + name + ");");
|
||||
} else if (type.equals(CtClass.longType) || type.getName().equals("java.lang.Long")) {
|
||||
return "writeLong(" + name + ")";
|
||||
return writeWrap(field, "out.writeLong(" + name + ");");
|
||||
} else if (type.equals(CtClass.floatType) || type.getName().equals("java.lang.Float")) {
|
||||
return "writeFloat(" + name + ")";
|
||||
return writeWrap(field, "out.writeFloat(" + name + ");");
|
||||
} else if (type.equals(CtClass.doubleType) || type.getName().equals("java.lang.Double")) {
|
||||
return "writeDouble(" + name + ")";
|
||||
return writeWrap(field, "out.writeDouble(" + name + ");");
|
||||
} else if (type.getName().equals("java.lang.String")) {
|
||||
return "writeUTF(" + name + ")";
|
||||
return writeWrap(field, "out.writeUTF(" + name + ");");
|
||||
}
|
||||
|
||||
if (type.isArray()) {
|
||||
CtClass ctype = type.getComponentType();
|
||||
if (ctype.equals(CtClass.booleanType)) {
|
||||
return writeWrap(field, BSNAME + ".writeBooleanArray(out, " + name + ");");
|
||||
} else if (ctype.equals(CtClass.byteType)) {
|
||||
return writeWrap(field, BSNAME + ".writeByteArray(out, " + name + ");");
|
||||
} else if (ctype.equals(CtClass.shortType)) {
|
||||
return writeWrap(field, BSNAME + ".writeShortArray(out, " + name + ");");
|
||||
} else if (ctype.equals(CtClass.intType)) {
|
||||
return writeWrap(field, BSNAME + ".writeIntArray(out, " + name + ");");
|
||||
} else if (ctype.equals(CtClass.longType)) {
|
||||
return writeWrap(field, BSNAME + ".writeLongArray(out, " + name + ");");
|
||||
} else if (ctype.equals(CtClass.floatType)) {
|
||||
return writeWrap(field, BSNAME + ".writeFloat(out, " + name + ");");
|
||||
} else if (ctype.equals(CtClass.doubleType)) {
|
||||
return writeWrap(field, BSNAME + ".writeDoubleArray(out, " + name + ");");
|
||||
} else if (ctype.getName().equals("java.lang.Object")) {
|
||||
return writeWrap(field, BSNAME + ".writeObjectArray(out, " + name + ");");
|
||||
}
|
||||
}
|
||||
|
||||
return writeWrap(field, "out.writeObject(" + name + ");");
|
||||
}
|
||||
|
||||
protected String readWrap (CtField field, String body)
|
||||
throws NotFoundException
|
||||
{
|
||||
if (field.getType().isPrimitive()) {
|
||||
return body;
|
||||
} else {
|
||||
return "writeObject(" + name + ")";
|
||||
return "if (ins.readBoolean()) {\n" +
|
||||
" " + body + "\n" +
|
||||
" } else {\n" +
|
||||
" " + field.getName() + " = null;\n" +
|
||||
" }";
|
||||
}
|
||||
}
|
||||
|
||||
protected String writeWrap (CtField field, String body)
|
||||
throws NotFoundException
|
||||
{
|
||||
if (field.getType().isPrimitive()) {
|
||||
return body;
|
||||
} else {
|
||||
return "if (" + field.getName() + " == null) {\n" +
|
||||
" out.writeBoolean(false);\n" +
|
||||
" } else {\n" +
|
||||
" out.writeBoolean(true);\n" +
|
||||
" " + body + "\n" +
|
||||
" }";
|
||||
}
|
||||
}
|
||||
|
||||
@@ -280,4 +345,9 @@ public class InstrumentStreamableTask extends Task
|
||||
|
||||
/** Used to instrument class files. */
|
||||
protected ClassPool _pool = ClassPool.getDefault();
|
||||
|
||||
/** Used to determine which classes implement {@link Streamable}. */
|
||||
protected CtClass _streamable;
|
||||
|
||||
protected static final String BSNAME = BasicStreamers.class.getName();
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user