StreamingContext _context;
SerializationBinder _binder;
-#if NET_1_1
TypeFilterLevel _filterLevel;
-#endif
ObjectManager _manager;
Hashtable _registeredAssemblies = new Hashtable();
_binder = formatter.Binder;
_manager = new ObjectManager (_surrogateSelector, _context);
-#if NET_1_1
_filterLevel = formatter.FilterLevel;
-#endif
}
public void ReadObjectGraph (BinaryReader reader, bool readHeaders, out object result, out Header[] headers)
info = metadata.NeedsSerializationInfo ? new SerializationInfo(metadata.Type, new FormatterConverter()) : null;
- if (metadata.MemberNames != null)
+ if (metadata.MemberNames != null) {
for (int n=0; n<metadata.FieldCount; n++)
ReadValue (reader, objectInstance, objectId, info, metadata.MemberTypes[n], metadata.MemberNames[n], null, null);
- else
- for (int n=0; n<metadata.FieldCount; n++)
- ReadValue (reader, objectInstance, objectId, info, metadata.MemberTypes[n], metadata.MemberInfos[n].Name, metadata.MemberInfos[n], null);
+ } else
+ for (int n=0; n<metadata.FieldCount; n++) {
+ if (metadata.MemberInfos [n] != null)
+ ReadValue (reader, objectInstance, objectId, info, metadata.MemberTypes[n], metadata.MemberInfos[n].Name, metadata.MemberInfos[n], null);
+ else if (BinaryCommon.IsPrimitive(metadata.MemberTypes[n])) {
+ // Since the member info is null, the type in this
+ // domain does not have this type. Even though we
+ // are not going to store the value, we will read
+ // it from the stream so that we can advance to the
+ // next block.
+ ReadPrimitiveTypeValue (reader, metadata.MemberTypes[n]);
+ }
+ }
}
private void RegisterObject (long objectId, object objectInstance, SerializationInfo info, long parentObjectId, MemberInfo parentObjectMemeber, int[] indices)
for (int n=0; n<fieldCount; n++)
codes [n] = (TypeTag) reader.ReadByte ();
- for (int n=0; n<fieldCount; n++)
- types [n] = ReadType (reader, codes[n]);
+ for (int n=0; n<fieldCount; n++) {
+ Type t = ReadType (reader, codes[n], false);
+ // The field's type could not be resolved: assume it is an object.
+ if (t == null)
+ t = typeof (object);
+ types [n] = t;
+ }
}
// Gets the type
else
field = metadata.Type.GetField (memberName, BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);
- if (field == null) throw new SerializationException ("Field \"" + names[n] + "\" not found in class " + metadata.Type.FullName);
- metadata.MemberInfos [n] = field;
+ if (field != null)
+ metadata.MemberInfos [n] = field;
if (!hasTypeInfo) {
types [n] = field.FieldType;
return metadata;
}
+ // Called for primitive types
+ static bool IsGeneric (MemberInfo minfo)
+ {
+ if (minfo == null)
+ return false;
+
+ Type mtype = null;
+ switch (minfo.MemberType) {
+ case MemberTypes.Field:
+ mtype = ((FieldInfo) minfo).FieldType;
+ break;
+ default:
+ throw new NotSupportedException ("Not supported: " + minfo.MemberType);
+ }
+ return (mtype != null && mtype.IsGenericType);
+ }
private void ReadValue (BinaryReader reader, object parentObject, long parentObjectId, SerializationInfo info, Type valueType, string fieldName, MemberInfo memberInfo, int[] indices)
{
object val;
- if (BinaryCommon.IsPrimitive (valueType))
+ if (BinaryCommon.IsPrimitive (valueType) && !IsGeneric (memberInfo))
{
val = ReadPrimitiveTypeValue (reader, valueType);
SetObjectValue (parentObject, fieldName, memberInfo, info, val, valueType, indices);
}
private Type GetDeserializationType (long assemblyId, string className)
+ {
+ return GetDeserializationType (assemblyId, className, true);
+ }
+
+ private Type GetDeserializationType (long assemblyId, string className, bool throwOnError)
{
Type t;
string assemblyName = (string)_registeredAssemblies[assemblyId];
if (t != null)
return t;
}
-
- Assembly assembly = Assembly.Load (assemblyName);
- t = assembly.GetType (className, true);
+
+ Assembly assembly;
+ try {
+ assembly = Assembly.Load (assemblyName);
+ } catch (Exception ex) {
+ if (!throwOnError)
+ return null;
+ throw new SerializationException (String.Format ("Couldn't find assembly '{0}'", assemblyName), ex);
+ }
+
+ t = assembly.GetType (className);
if (t != null)
return t;
- throw new SerializationException ("Couldn't find type '" + className + "'.");
+
+ if (!throwOnError)
+ return null;
+
+ throw new SerializationException (String.Format ("Couldn't find type '{0}' in assembly '{1}'", className, assemblyName));
}
public Type ReadType (BinaryReader reader, TypeTag code)
+ {
+ return ReadType (reader, code, true);
+ }
+
+ public Type ReadType (BinaryReader reader, TypeTag code, bool throwOnError)
{
switch (code)
{
{
string name = reader.ReadString ();
long asmid = (long) reader.ReadUInt32();
- return GetDeserializationType (asmid, name);
+ return GetDeserializationType (asmid, name, throwOnError);
}
case TypeTag.ArrayOfObject: