Skip to content

Commit

Permalink
System.Private.Xml AOT compatibility fixes (#76473)
Browse files Browse the repository at this point in the history
* Fix AOT warnings from using the linker xml support in crossgen2.

* Revise message to better explain why these types will be available.

* Remove suppressions and change implementation to not require suppressions.

Co-authored-by: Eric Erhardt <eric.erhardt@microsoft.com>
Co-authored-by: Jan Kotas <jkotas@microsoft.com>
  • Loading branch information
3 people committed Oct 4, 2022
1 parent c23241b commit 6294ab1
Show file tree
Hide file tree
Showing 4 changed files with 39 additions and 11 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -1439,7 +1439,7 @@ private void CheckUniqueParticleAttribution(BitSet curpos)
int symbolsCount = _symbols!.Count;

// transition table (Dtran in the book)
ArrayList transitionTable = new ArrayList();
List<int[]> transitionTable = new();

// state lookup table (Dstate in the book)
Dictionary<BitSet, int> stateTable = new();
Expand All @@ -1461,7 +1461,7 @@ private void CheckUniqueParticleAttribution(BitSet curpos)
{
BitSet statePosSet = unmarked.Dequeue(); // all positions that constitute DFA state
Debug.Assert(state == stateTable[statePosSet]); // just make sure that statePosSet is for correct state
int[] transition = (int[])transitionTable[state]!;
int[] transition = transitionTable[state]!;
if (statePosSet[endMarkerPos])
{
transition[symbolsCount] = 1; // accepting
Expand Down Expand Up @@ -1506,7 +1506,7 @@ private void CheckUniqueParticleAttribution(BitSet curpos)
state++;
}
// now convert transition table to array
return (int[][])transitionTable.ToArray(typeof(int[]));
return transitionTable.ToArray();
}

#if DEBUG
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@
using System.IO;
using System.Collections;
using System.Diagnostics;
using System.Diagnostics.CodeAnalysis;
using System.Globalization;
using System.Text;
using System.Text.RegularExpressions;
Expand Down Expand Up @@ -521,8 +522,6 @@ internal override bool HasValueFacets

protected DatatypeImplementation? Base { get { return _baseType; } }

internal abstract Type ListValueType { get; }

internal abstract RestrictionFlags ValidRestrictionFlags { get; }

internal override XmlSchemaWhiteSpace BuiltInWhitespaceFacet { get { return XmlSchemaWhiteSpace.Preserve; } }
Expand Down Expand Up @@ -1126,8 +1125,8 @@ internal override RestrictionFlags ValidRestrictionFlags

values.Add(typedValue);
}
array = values.ToArray(_itemType.ValueType);
Debug.Assert(array.GetType() == ListValueType);
Debug.Assert(_itemType.ListValueType.GetElementType() == _itemType.ValueType);
array = ToArray(values, _itemType.ListValueType);
}
if (values.Count < _minListSize)
{
Expand All @@ -1143,6 +1142,12 @@ internal override RestrictionFlags ValidRestrictionFlags

Error:
return exception;

// TODO: Replace with https://github.com/dotnet/runtime/issues/76478 once available
[UnconditionalSuppressMessage("AotAnalysis", "IL3050:AotUnfriendlyApi",
Justification = "Array type is always present as it is passed in as a parameter.")]
static Array ToArray(ArrayList values, Type arrayType)
=> values.ToArray(arrayType.GetElementType()!);
}
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,8 @@ public abstract class XmlSchemaDatatype

public virtual XmlSchemaDatatypeVariety Variety { get { return XmlSchemaDatatypeVariety.Atomic; } }

internal abstract Type ListValueType { get; }

internal XmlSchemaDatatype() { }

public virtual object ChangeType(object value, Type targetType)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
using System.Xml.XPath;
using System.Globalization;
using System.Diagnostics;
using System.Diagnostics.CodeAnalysis;
using System.Collections;
using System.Collections.Generic;
using System.Xml.Schema;
Expand Down Expand Up @@ -225,6 +226,7 @@ internal abstract class XmlBaseConverter : XmlValueConverter
private readonly XmlSchemaType? _schemaType;
private readonly XmlTypeCode _typeCode;
private readonly Type? _clrTypeDefault;
private readonly Type? _clrListTypeDefault;

protected XmlBaseConverter(XmlSchemaType schemaType)
{
Expand All @@ -242,6 +244,7 @@ protected XmlBaseConverter(XmlSchemaType schemaType)
_schemaType = schemaType;
_typeCode = schemaType.TypeCode;
_clrTypeDefault = schemaType.Datatype.ValueType;
_clrListTypeDefault = schemaType.Datatype.ListValueType;
}

protected XmlBaseConverter(XmlTypeCode typeCode)
Expand All @@ -250,14 +253,17 @@ protected XmlBaseConverter(XmlTypeCode typeCode)
{
case XmlTypeCode.Item:
_clrTypeDefault = XPathItemType;
_clrListTypeDefault = XPathItemArrayType;
break;

case XmlTypeCode.Node:
_clrTypeDefault = XPathNavigatorType;
_clrListTypeDefault = XPathNavigatorArrayType;
break;

case XmlTypeCode.AnyAtomicType:
_clrTypeDefault = XmlAtomicValueType;
_clrListTypeDefault = XmlAtomicValueArrayType;
break;

default:
Expand All @@ -272,22 +278,29 @@ protected XmlBaseConverter(XmlBaseConverter converterAtomic)
{
_schemaType = converterAtomic._schemaType;
_typeCode = converterAtomic._typeCode;
_clrTypeDefault = Array.CreateInstance(converterAtomic.DefaultClrType!, 0).GetType();
_clrTypeDefault = converterAtomic.DefaultClrListType;
Debug.Assert(_clrTypeDefault!.IsArray);
// We don't support lists-of-lists, so we set _clrListTypeDefault to null.
_clrListTypeDefault = null;
}

protected XmlBaseConverter(XmlBaseConverter converterAtomic, Type clrTypeDefault)
protected XmlBaseConverter(XmlBaseConverter converterAtomic, Type clrTypeDefault, Type clrListTypeDefault)
{
_schemaType = converterAtomic._schemaType;
_typeCode = converterAtomic._typeCode;
_clrTypeDefault = clrTypeDefault;
_clrListTypeDefault = clrListTypeDefault;
}

protected static readonly Type ICollectionType = typeof(ICollection);
protected static readonly Type IEnumerableType = typeof(IEnumerable);
protected static readonly Type IListType = typeof(IList);
protected static readonly Type ObjectArrayType = typeof(object[]);
protected static readonly Type StringArrayType = typeof(string[]);
protected static readonly Type StringArrayArrayType = typeof(string[][]);
protected static readonly Type XmlAtomicValueArrayType = typeof(XmlAtomicValue[]);
protected static readonly Type XPathItemArrayType = typeof(XPathItem[]);
protected static readonly Type XPathNavigatorArrayType = typeof(XPathNavigator[]);

#region AUTOGENERATED_XMLBASECONVERTER
protected static readonly Type DecimalType = typeof(decimal);
Expand Down Expand Up @@ -432,6 +445,14 @@ protected Type? DefaultClrType
get { return _clrTypeDefault; }
}

/// <summary>
/// Return an array type with the element type of the default V1 Clr mapping of this converter's type.
/// </summary>
protected Type? DefaultClrListType
{
get { return _clrListTypeDefault; }
}

/// <summary>
/// Type.IsSubtypeOf does not return true if types are equal, this method does.
/// </summary>
Expand Down Expand Up @@ -1988,7 +2009,7 @@ private XmlUntypedConverter() : base(DatatypeImplementation.UntypedAtomicType)
}

private XmlUntypedConverter(XmlUntypedConverter atomicConverter, bool allowListToList)
: base(atomicConverter, allowListToList ? StringArrayType : StringType)
: base(atomicConverter, allowListToList ? StringArrayType : StringType, allowListToList ? StringArrayArrayType : StringArrayType)
{
_allowListToList = allowListToList;
}
Expand Down Expand Up @@ -2875,7 +2896,7 @@ protected XmlListConverter(XmlBaseConverter atomicConverter) : base(atomicConver
this.atomicConverter = atomicConverter;
}

protected XmlListConverter(XmlBaseConverter atomicConverter, Type clrTypeDefault) : base(atomicConverter, clrTypeDefault)
protected XmlListConverter(XmlBaseConverter atomicConverter, Type clrTypeDefault, Type clrListTypeDefault) : base(atomicConverter, clrTypeDefault, clrListTypeDefault)
{
this.atomicConverter = atomicConverter;
}
Expand Down

0 comments on commit 6294ab1

Please sign in to comment.