You've already forked linux-packaging-mono
Imported Upstream version 4.0.0~alpha1
Former-commit-id: 806294f5ded97629b74c85c09952f2a74fe182d9
This commit is contained in:
76
external/referencesource/System.Web/Util/Utf16StringValidator.cs
vendored
Normal file
76
external/referencesource/System.Web/Util/Utf16StringValidator.cs
vendored
Normal file
@ -0,0 +1,76 @@
|
||||
//------------------------------------------------------------------------------
|
||||
// <copyright file="Utf16StringValidator.cs" company="Microsoft">
|
||||
// Copyright (c) Microsoft Corporation. All rights reserved.
|
||||
// </copyright>
|
||||
//------------------------------------------------------------------------------
|
||||
|
||||
namespace System.Web.Util {
|
||||
using System;
|
||||
|
||||
// This class contains utility methods for dealing with security contexts when crossing AppDomain boundaries.
|
||||
|
||||
internal static class Utf16StringValidator {
|
||||
|
||||
private const char UNICODE_NULL_CHAR = '\0';
|
||||
private const char UNICODE_REPLACEMENT_CHAR = '\uFFFD';
|
||||
|
||||
private static readonly bool _skipUtf16Validation = AppSettings.AllowRelaxedUnicodeDecoding;
|
||||
|
||||
public static string ValidateString(string input) {
|
||||
return ValidateString(input, _skipUtf16Validation);
|
||||
}
|
||||
|
||||
// only internal for unit testing
|
||||
internal static string ValidateString(string input, bool skipUtf16Validation) {
|
||||
if (skipUtf16Validation || String.IsNullOrEmpty(input)) {
|
||||
return input;
|
||||
}
|
||||
|
||||
// locate the first surrogate character
|
||||
int idxOfFirstSurrogate = -1;
|
||||
for (int i = 0; i < input.Length; i++) {
|
||||
if (Char.IsSurrogate(input[i])) {
|
||||
idxOfFirstSurrogate = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
// fast case: no surrogates = return input string
|
||||
if (idxOfFirstSurrogate < 0) {
|
||||
return input;
|
||||
}
|
||||
|
||||
// slow case: surrogates exist, so we need to validate them
|
||||
char[] chars = input.ToCharArray();
|
||||
for (int i = idxOfFirstSurrogate; i < chars.Length; i++) {
|
||||
char thisChar = chars[i];
|
||||
|
||||
// If this character is a low surrogate, then it was not preceded by
|
||||
// a high surrogate, so we'll replace it.
|
||||
if (Char.IsLowSurrogate(thisChar)) {
|
||||
chars[i] = UNICODE_REPLACEMENT_CHAR;
|
||||
continue;
|
||||
}
|
||||
|
||||
if (Char.IsHighSurrogate(thisChar)) {
|
||||
// If this character is a high surrogate and it is followed by a
|
||||
// low surrogate, allow both to remain.
|
||||
if (i + 1 < chars.Length && Char.IsLowSurrogate(chars[i + 1])) {
|
||||
i++; // skip the low surrogate also
|
||||
continue;
|
||||
}
|
||||
|
||||
// If this character is a high surrogate and it is not followed
|
||||
// by a low surrogate, replace it.
|
||||
chars[i] = UNICODE_REPLACEMENT_CHAR;
|
||||
continue;
|
||||
}
|
||||
|
||||
// Otherwise, this is a non-surrogate character and just move to the
|
||||
// next character.
|
||||
}
|
||||
return new String(chars);
|
||||
}
|
||||
|
||||
}
|
||||
}
|
Reference in New Issue
Block a user