// Path: core/src/main/java/com/threerings/nexus/distrib/DService.java
// public abstract class DService<T extends NexusService> implements DAttribute
// {
//     /** Used to create service attributes. */
//     public interface Factory<T extends NexusService>
//     {
//         /** Creates a service attribute with the supplied owner. */
//         DService<T> createService (NexusObject owner);
//     }
// 
//     /** An implementation detail used by service dispatchers. */
//     public static abstract class Dispatcher<T extends NexusService> extends DService<T> {
//         /** Dispatches a service call that came in over the network. */
//         public RFuture<?> dispatchCall (short methodId, Object[] args) {
//             throw new IllegalArgumentException("Unknown service method [id=" + methodId +
//                                                ", obj=" + _owner.getClass().getName() +
//                                                ", attrIdx=" + _index + "]");
//         }
// 
//         protected Dispatcher (NexusObject owner) {
//             super(owner);
//         }
// 
//         /** Used to concisely, and without warning, cast arguments of generic type. */
//         @SuppressWarnings("unchecked")
//         protected final <C> C cast (Object obj) {
//             return (C)obj;
//         }
//     }
// 
//     /** Returns the service encapsulated by this attribute. */
//     public abstract T get ();
// 
//     /** Returns the class for the service encapsulated by this attribute. */
//     public abstract Class<T> getServiceClass ();
// 
//     @Override public void readContents (Streamable.Input in) {
//         // NOOP
//     }
// 
//     @Override public void writeContents (Streamable.Output out) {
//         // NOOP
//     }
// 
//     protected DService (NexusObject owner) {
//         _owner = owner;
//         _index = owner.registerAttr(this);
//     }
// 
//     /** Used by marshallers to dispatch calls over the network. */
//     protected <R> RFuture<R> postCall (short methodId, Object... args) {
//         RPromise<R> result = RPromise.create();
//         _owner.postCall(_index, methodId, args, result);
//         return result;
//     }
// 
//     /** Used by marshallers to dispatch calls over the network. */
//     protected void postVoidCall (short methodId, Object... args) {
//         _owner.postCall(_index, methodId, args, null);
//     }
// 
//     /** The object that owns this attribute. */
//     protected final NexusObject _owner;
// 
//     /** The index of this attribute in its containing object. */
//     protected final short _index;
// }
// 
// Path: core/src/main/java/com/threerings/nexus/distrib/NexusException.java
// public class NexusException extends RuntimeException
//     implements Streamable
// {
//     /**
//      * Throws a NexusException with the supplied error message if {@code condition} is not true.
//      */
//     public static void require (boolean condition, String errmsg, Object... args) {
//         if (!condition) throw new NexusException(Log.format(errmsg, args));
//     }
// 
//     public NexusException (String message) {
//         super(message);
//     }
// 
//     public NexusException (String message, Throwable cause) {
//         super(message, cause);
//     }
// 
//     public NexusException (Throwable cause) {
//         super(cause);
//     }
// }
// 
// Path: core/src/main/java/com/threerings/nexus/distrib/NexusService.java
// public interface NexusService
// {
// }


import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import com.threerings.nexus.distrib.DService;
import com.threerings.nexus.distrib.NexusException;
import com.threerings.nexus.distrib.NexusService;
        return nonNull(_serviceCodes.get(clazz), "Unknown service class ", clazz);
    }

    // from interface Serializer
    public <T> Streamer<T> writeStreamer (Streamable.Output out, T value) {
        if (value == null) {
            return this.<T>writeClass(out, (short)0); // null streamer has code 0
        }

        // if the class is known, just look up the code and write it
        Class<?> vclass = value.getClass();
        Short code = _codes.get(vclass);
        if (code != null) {
            return this.<T>writeClass(out, code);
        }

        // if the class is some more obscure subtype of list/set/map, use the stock
        // streamer and cache this type with the same code
        if (value instanceof List) {
            _codes.put(vclass, code = _codes.get(ArrayList.class));
            return this.<T>writeClass(out, code);
        } else if (value instanceof Set) {
            _codes.put(vclass, code = _codes.get(HashSet.class));
            return this.<T>writeClass(out, code);
        } else if (value instanceof Map) {
            _codes.put(vclass, code = _codes.get(HashMap.class));
            return this.<T>writeClass(out, code);
        }

        // otherwise: houston, we have a problem
// Path: core/src/main/java/com/threerings/nexus/distrib/DService.java
// public abstract class DService<T extends NexusService> implements DAttribute
// {
//     /** Used to create service attributes. */
//     public interface Factory<T extends NexusService>
//     {
//         /** Creates a service attribute with the supplied owner. */
//         DService<T> createService (NexusObject owner);
//     }
// 
//     /** An implementation detail used by service dispatchers. */
//     public static abstract class Dispatcher<T extends NexusService> extends DService<T> {
//         /** Dispatches a service call that came in over the network. */
//         public RFuture<?> dispatchCall (short methodId, Object[] args) {
//             throw new IllegalArgumentException("Unknown service method [id=" + methodId +
//                                                ", obj=" + _owner.getClass().getName() +
//                                                ", attrIdx=" + _index + "]");
//         }
// 
//         protected Dispatcher (NexusObject owner) {
//             super(owner);
//         }
// 
//         /** Used to concisely, and without warning, cast arguments of generic type. */
//         @SuppressWarnings("unchecked")
//         protected final <C> C cast (Object obj) {
//             return (C)obj;
//         }
//     }
// 
//     /** Returns the service encapsulated by this attribute. */
//     public abstract T get ();
// 
//     /** Returns the class for the service encapsulated by this attribute. */
//     public abstract Class<T> getServiceClass ();
// 
//     @Override public void readContents (Streamable.Input in) {
//         // NOOP
//     }
// 
//     @Override public void writeContents (Streamable.Output out) {
//         // NOOP
//     }
// 
//     protected DService (NexusObject owner) {
//         _owner = owner;
//         _index = owner.registerAttr(this);
//     }
// 
//     /** Used by marshallers to dispatch calls over the network. */
//     protected <R> RFuture<R> postCall (short methodId, Object... args) {
//         RPromise<R> result = RPromise.create();
//         _owner.postCall(_index, methodId, args, result);
//         return result;
//     }
// 
//     /** Used by marshallers to dispatch calls over the network. */
//     protected void postVoidCall (short methodId, Object... args) {
//         _owner.postCall(_index, methodId, args, null);
//     }
// 
//     /** The object that owns this attribute. */
//     protected final NexusObject _owner;
// 
//     /** The index of this attribute in its containing object. */
//     protected final short _index;
// }
// 
// Path: core/src/main/java/com/threerings/nexus/distrib/NexusException.java
// public class NexusException extends RuntimeException
//     implements Streamable
// {
//     /**
//      * Throws a NexusException with the supplied error message if {@code condition} is not true.
//      */
//     public static void require (boolean condition, String errmsg, Object... args) {
//         if (!condition) throw new NexusException(Log.format(errmsg, args));
//     }
// 
//     public NexusException (String message) {
//         super(message);
//     }
// 
//     public NexusException (String message, Throwable cause) {
//         super(message, cause);
//     }
// 
//     public NexusException (Throwable cause) {
//         super(cause);
//     }
// }
// 
// Path: core/src/main/java/com/threerings/nexus/distrib/NexusService.java
// public interface NexusService
// {
// }


// Path: core/src/main/java/com/threerings/nexus/io/AbstractSerializer.java
import java.util.ArrayList;
import java.util.HashMap;
import java.util.HashSet;
import java.util.List;
import java.util.Map;
import java.util.Set;
import com.threerings.nexus.distrib.DService;
import com.threerings.nexus.distrib.NexusException;
import com.threerings.nexus.distrib.NexusService;

        return nonNull(_serviceCodes.get(clazz), "Unknown service class ", clazz);
    }

    // from interface Serializer
    public <T> Streamer<T> writeStreamer (Streamable.Output out, T value) {
        if (value == null) {
            return this.<T>writeClass(out, (short)0); // null streamer has code 0
        }

        // if the class is known, just look up the code and write it
        Class<?> vclass = value.getClass();
        Short code = _codes.get(vclass);
        if (code != null) {
            return this.<T>writeClass(out, code);
        }

        // if the class is some more obscure subtype of list/set/map, use the stock
        // streamer and cache this type with the same code
        if (value instanceof List) {
            _codes.put(vclass, code = _codes.get(ArrayList.class));
            return this.<T>writeClass(out, code);
        } else if (value instanceof Set) {
            _codes.put(vclass, code = _codes.get(HashSet.class));
            return this.<T>writeClass(out, code);
        } else if (value instanceof Map) {
            _codes.put(vclass, code = _codes.get(HashMap.class));
            return this.<T>writeClass(out, code);
        }

        // otherwise: houston, we have a problem
        throw new NexusException("Requested to stream unknown type " + vclass);