private static SHUnionPropertyCache GetCachedProperties(Type type) { if (PropertyCache.ContainsKey(type)) { return(PropertyCache[type]); } var x = new SHUnionPropertyCache { TypeProperty = type.GetProperty("Type"), ValueProperty = type.GetProperty("Value") }; PropertyCache.Add(type, x); return(x); }
/// <inheritdoc /> public object Deserialize(BinaryReader reader, ControllerSerializationContext serializationContext) { long dataSize = reader.BaseStream.Length - reader.BaseStream.Position; SHUnionPropertyCache propertyCache = GetCachedProperties(serializationContext.Type); Type[] typeArgs = serializationContext.Type.GetGenericArguments(); // Using size of data to determine which of the SHUnion generic type arguments to use. Type valueType = typeArgs.FirstOrDefault(type => Marshal.SizeOf(type) == dataSize); if (valueType == null) { throw new SilentHunterParserException($"The available stream data does not match the size one of the two union types for property '{serializationContext.Name}'."); } object union = Activator.CreateInstance(serializationContext.Type); propertyCache.TypeProperty.SetValue(union, valueType, null); propertyCache.ValueProperty.SetValue(union, reader.ReadStruct(valueType), null); return(union); }
/// <inheritdoc /> public void Serialize(BinaryWriter writer, ControllerSerializationContext serializationContext, object value) { SHUnionPropertyCache propertyCache = GetCachedProperties(serializationContext.Type); writer.WriteStruct(propertyCache.ValueProperty.GetValue(value, null)); }