Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Remove string allocation from XmlTextEncoder.WriteCharEntity #61774

Closed
Original file line number Diff line number Diff line change
Expand Up @@ -231,11 +231,11 @@ internal void Write(char[] array, int offset, int count)

internal void WriteSurrogateCharEntity(char lowChar, char highChar)
{
if (!XmlCharType.IsLowSurrogate(lowChar) ||
!XmlCharType.IsHighSurrogate(highChar))
if (!XmlCharType.IsLowSurrogate(lowChar) || !XmlCharType.IsHighSurrogate(highChar))
{
throw XmlConvert.CreateInvalidSurrogatePairException(lowChar, highChar);
}

int surrogateChar = XmlCharType.CombineSurrogateChar(lowChar, highChar);

if (_cacheAttrValue)
Expand All @@ -245,9 +245,9 @@ internal void WriteSurrogateCharEntity(char lowChar, char highChar)
_attrValue.Append(lowChar);
}

_textWriter.Write("&#x");
_textWriter.Write(surrogateChar.ToString("X", NumberFormatInfo.InvariantInfo));
_textWriter.Write(';');
Span<char> span = stackalloc char[12];
int charsWritten = WriteCharToSpan(span, surrogateChar);
_textWriter.Write(span[..charsWritten]);
}

internal void Write(string text)
Expand Down Expand Up @@ -479,25 +479,24 @@ internal void WriteRaw(char[] array, int offset, int count)
_textWriter.Write(array, offset, count);
}



internal void WriteCharEntity(char ch)
{
if (XmlCharType.IsSurrogate(ch))
{
throw new ArgumentException(SR.Xml_InvalidSurrogateMissingLowChar);
}

string strVal = ((int)ch).ToString("X", NumberFormatInfo.InvariantInfo);
Span<char> span = stackalloc char[12];
int charsWritten = WriteCharToSpan(span, ch);
ReadOnlySpan<char> ros = span[..charsWritten];

if (_cacheAttrValue)
{
Debug.Assert(_attrValue != null);
_attrValue.Append("&#x");
_attrValue.Append(strVal);
_attrValue.Append(';');
_attrValue.Append(ros);
}

WriteCharEntityImpl(strVal);
_textWriter.Write(ros);
}

internal void WriteEntityRef(string name)
Expand Down Expand Up @@ -540,14 +539,21 @@ private void WriteStringFragment(string str, int offset, int count, char[] helpe

private void WriteCharEntityImpl(char ch)
{
WriteCharEntityImpl(((int)ch).ToString("X", NumberFormatInfo.InvariantInfo));
Span<char> span = stackalloc char[12];
int charsWritten = WriteCharToSpan(span, ch);
_textWriter.Write(span[..charsWritten]);
}

private void WriteCharEntityImpl(string strVal)
private static int WriteCharToSpan(Span<char> destination, int ch)
{
_textWriter.Write("&#x");
_textWriter.Write(strVal);
_textWriter.Write(';');
Debug.Assert(destination.Length >= 12);
destination[0] = '&';
destination[1] = '#';
destination[2] = 'x';
bool result = ch.TryFormat(destination[3..], out int charsWritten, "X", NumberFormatInfo.InvariantInfo);
Debug.Assert(result);
destination[charsWritten + 3] = ';';
return charsWritten + 4;
}

private void WriteEntityRefImpl(string name)
Expand Down