private IMessage[] ApplyPatchesAndDeserialize(SerializationPatcher serializationPatcher, XmlDocument xmlDocument)
		{
			var patchedText = serializationPatcher.Apply(xmlDocument.InnerXml);
			var patchedXmlDocument = new XmlDocument();
			patchedXmlDocument.LoadXml(patchedText);
			return Deserialize(patchedXmlDocument).Item1;
		}
		public IMessage[] Deserialize(Stream stream)
		{
			var xmlDocument = new XmlDocument();
			xmlDocument.Load(stream);
			var result = Deserialize(xmlDocument);

			var notFoundTypesCount = result.Item2;
			if (notFoundTypesCount == 0)
			{
				return result.Item1;
			}

			var serializationPatcher = new SerializationPatcher(new IPatch[] {});
			if (!serializationPatcher.ShouldApply(xmlDocument.InnerXml))
			{
				return result.Item1;
			}

			return ApplyPatchesAndDeserialize(serializationPatcher, xmlDocument);
		}
		public static object Deserialize(XDocument stateData, string keyType)
		{
			try
			{
				return DeserializeInternal(stateData, keyType);
			}
			catch (Exception)
			{
				var reader = stateData.CreateReader();
				reader.MoveToContent();
				var readOuterXml = reader.ReadOuterXml();
				var serializationPatcher = new SerializationPatcher(new[] { new RemoveBackingFieldPatch(keyType) });
				if (serializationPatcher.ShouldApply(readOuterXml))
				{
					var patchedText = serializationPatcher.Apply(readOuterXml);
					return DeserializeInternal(XDocument.Parse(patchedText), keyType);
				}

				throw;
			}
		}