* Use official Type.GetTypeCode() instead of the extension that was added to fill the gap in the earlier days of .Net Core.
* Bring reflection-based serializer in line with RefEmit behavior for 'object' serialization.
<Compile Include="System\Xml\Serialization\Configuration\DateTimeSerializationSection.cs" />
<Compile Include="System\Xml\Extensions\ExtensionMethods.cs" />
<Compile Include="System\Xml\Serialization\Globals.cs" />
- <Compile Include="System\Xml\Serialization\TypeCode.cs" />
</ItemGroup>
<!-- Embedded DTD files -->
<ItemGroup>
internal void Ldobj(Type type)
{
- OpCode opCode = GetLdindOpCode(type.GetTypeCode());
+ OpCode opCode = GetLdindOpCode(Type.GetTypeCode(type));
if (!opCode.Equals(OpCodes.Nop))
{
_ilGen!.Emit(opCode);
}
else
{
- switch (valueType.GetTypeCode())
+ switch (Type.GetTypeCode(valueType))
{
case TypeCode.Boolean:
Ldc((bool)o);
}
else
{
- OpCode opCode = GetLdelemOpCode(arrayElementType.GetTypeCode());
+ OpCode opCode = GetLdelemOpCode(Type.GetTypeCode(arrayElementType));
Debug.Assert(!opCode.Equals(OpCodes.Nop));
if (opCode.Equals(OpCodes.Nop))
throw new InvalidOperationException(SR.Format(SR.ArrayTypeIsNotSupported, arrayElementType.AssemblyQualifiedName));
Stelem(Enum.GetUnderlyingType(arrayElementType));
else
{
- OpCode opCode = GetStelemOpCode(arrayElementType.GetTypeCode());
+ OpCode opCode = GetStelemOpCode(Type.GetTypeCode(arrayElementType));
if (opCode.Equals(OpCodes.Nop))
throw new InvalidOperationException(SR.Format(SR.ArrayTypeIsNotSupported, arrayElementType.AssemblyQualifiedName));
_ilGen!.Emit(opCode);
{
if (source.IsValueType)
{
- OpCode opCode = GetConvOpCode(target.GetTypeCode());
+ OpCode opCode = GetConvOpCode(Type.GetTypeCode(target));
if (opCode.Equals(OpCodes.Nop))
{
throw new CodeGeneratorConversionException(source, target, isAddress, "NoConversionPossibleTo");
[RequiresUnreferencedCode("calls WriteMember")]
private bool WriteEnumAndArrayTypes(StructMapping structMapping, object o, string n, string? ns)
{
- if (o is Enum)
- {
- Writer.WriteStartElement(n, ns);
+ Type objType = o.GetType();
- EnumMapping? enumMapping = null;
- Type enumType = o.GetType();
- foreach (var m in _mapping.Scope!.TypeMappings)
+ foreach (var m in _mapping.Scope!.TypeMappings)
+ {
+ if (m is EnumMapping em && em.TypeDesc!.Type == objType)
{
- if (m is EnumMapping em && em.TypeDesc!.Type == enumType)
- {
- enumMapping = em;
- break;
- }
+ Writer.WriteStartElement(n, ns);
+ WriteXsiType(em.TypeName!, ns);
+ Writer.WriteString(WriteEnumMethod(em, o));
+ Writer.WriteEndElement();
+ return true;
}
- if (enumMapping == null)
- throw new InvalidOperationException(SR.XmlInternalError);
-
- WriteXsiType(enumMapping.TypeName!, ns);
- Writer.WriteString(WriteEnumMethod(enumMapping, o));
- Writer.WriteEndElement();
- return true;
- }
-
- if (o is Array)
- {
- Writer.WriteStartElement(n, ns);
- ArrayMapping? arrayMapping = null;
- Type arrayType = o.GetType();
- foreach (var m in _mapping.Scope!.TypeMappings)
+ if (m is ArrayMapping am && am.TypeDesc!.Type == objType)
{
- if (m is ArrayMapping am && am.TypeDesc!.Type == arrayType)
- {
- arrayMapping = am;
- break;
- }
+ Writer.WriteStartElement(n, ns);
+ WriteXsiType(am.TypeName!, ns);
+ WriteMember(o, null, am.ElementsSortedByDerivation!, null, null, am.TypeDesc!, true);
+ Writer.WriteEndElement();
+ return true;
}
-
- if (arrayMapping == null)
- throw new InvalidOperationException(SR.XmlInternalError);
-
- WriteXsiType(arrayMapping.TypeName!, ns);
- WriteMember(o, null, arrayMapping.ElementsSortedByDerivation!, null, null, arrayMapping.TypeDesc!, true);
- Writer.WriteEndElement();
-
- return true;
}
return false;
+++ /dev/null
-// Licensed to the .NET Foundation under one or more agreements.
-// The .NET Foundation licenses this file to you under the MIT license.
-
-namespace System.Xml.Serialization
-{
- using System;
-
- internal enum TypeCode
- {
- Empty = 0, // Null reference
- Object = 1, // Instance that isn't a value
- DBNull = 2, // Database null value
- Boolean = 3, // Boolean
- Char = 4, // Unicode character
- SByte = 5, // Signed 8-bit integer
- Byte = 6, // Unsigned 8-bit integer
- Int16 = 7, // Signed 16-bit integer
- UInt16 = 8, // Unsigned 16-bit integer
- Int32 = 9, // Signed 32-bit integer
- UInt32 = 10, // Unsigned 32-bit integer
- Int64 = 11, // Signed 64-bit integer
- UInt64 = 12, // Unsigned 64-bit integer
- Single = 13, // IEEE 32-bit float
- Double = 14, // IEEE 64-bit double
- Decimal = 15, // Decimal
- DateTime = 16, // DateTime
- String = 18, // Unicode character string
- }
-
- internal static class TypeExtensionMethods
- {
- public static TypeCode GetTypeCode(this Type type)
- {
- if (type == null)
- {
- return TypeCode.Empty;
- }
- else if (type == typeof(bool))
- {
- return TypeCode.Boolean;
- }
- else if (type == typeof(char))
- {
- return TypeCode.Char;
- }
- else if (type == typeof(sbyte))
- {
- return TypeCode.SByte;
- }
- else if (type == typeof(byte))
- {
- return TypeCode.Byte;
- }
- else if (type == typeof(short))
- {
- return TypeCode.Int16;
- }
- else if (type == typeof(ushort))
- {
- return TypeCode.UInt16;
- }
- else if (type == typeof(int))
- {
- return TypeCode.Int32;
- }
- else if (type == typeof(uint))
- {
- return TypeCode.UInt32;
- }
- else if (type == typeof(long))
- {
- return TypeCode.Int64;
- }
- else if (type == typeof(ulong))
- {
- return TypeCode.UInt64;
- }
- else if (type == typeof(float))
- {
- return TypeCode.Single;
- }
- else if (type == typeof(double))
- {
- return TypeCode.Double;
- }
- else if (type == typeof(decimal))
- {
- return TypeCode.Decimal;
- }
- else if (type == typeof(DateTime))
- {
- return TypeCode.DateTime;
- }
- else if (type == typeof(string))
- {
- return TypeCode.String;
- }
- else
- {
- return TypeCode.Object;
- }
- }
- }
-}
if (type.IsEnum)
return false;
- switch (type.GetTypeCode())
+ switch (Type.GetTypeCode(type))
{
case TypeCode.String: return true;
case TypeCode.Int32: return true;
string typeName;
string typeNs = XmlSchema.Namespace;
- switch (type.GetTypeCode())
+ switch (Type.GetTypeCode(type))
{
case TypeCode.String: typeName = "string"; break;
case TypeCode.Int32: typeName = "int"; break;
Type t = o.GetType();
bool wroteStartElement = false;
- switch (t.GetTypeCode())
+ switch (Type.GetTypeCode(t))
{
case TypeCode.String:
value = (string)o;
return;
}
Type t = o.GetType();
- if (t.GetTypeCode() == TypeCode.Object && !(o is Guid) && (t != typeof(XmlQualifiedName)) && !(o is XmlNode[]) && (t != typeof(byte[])))
+ if (Type.GetTypeCode(t) == TypeCode.Object && !(o is Guid) && (t != typeof(XmlQualifiedName)) && !(o is XmlNode[]) && (t != typeof(byte[])))
{
if ((suppressReference || _soap12) && !IsIdDefined(o))
{
{
XmlSerializationPrimitiveWriter writer = new XmlSerializationPrimitiveWriter();
writer.Init(xmlWriter, namespaces, null, null, null);
- switch (_primitiveType!.GetTypeCode())
+ switch (Type.GetTypeCode(_primitiveType))
{
case TypeCode.String:
writer.Write_string(o);
XmlSerializationPrimitiveReader reader = new XmlSerializationPrimitiveReader();
reader.Init(xmlReader, events, null, null);
object? o;
- switch (_primitiveType!.GetTypeCode())
+ switch (Type.GetTypeCode(_primitiveType))
{
case TypeCode.String:
o = reader.Read_string();
Assert.StrictEqual(x.P1, y.P1);
}
+#if !XMLSERIALIZERGENERATORTESTS
+ [Fact]
+ public static void Xml_EnumAsObject()
+ {
+ object o = MyEnum.Three;
+ object o2 = SerializeAndDeserialize<object>(o,
+@"<?xml version=""1.0"" encoding=""utf-8""?>
+<anyType xmlns:q1=""http://www.w3.org/2001/XMLSchema"" p2:type=""q1:int"" xmlns:p2=""http://www.w3.org/2001/XMLSchema-instance"">2</anyType>");
+ Assert.NotNull(o2);
+ Assert.StrictEqual((int)o, o2);
+ Assert.Equal(MyEnum.Three, (MyEnum)o2);
+ }
+#endif
+
[Fact]
public static void Xml_DCClassWithEnumAndStruct()
{