/
githubmirror
/
roslyn
Обзор
Документация
Войти
/
githubmirror
/
roslyn
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
main
src/ExpressionEvaluator/CSharp/Source/ResultProvider/CSharpFormatter.cs
125 строк
4 KB
Ramkumar Ramesh
[EE] Implement IDkmClrFullNameProvider2 in Roslyn's ResultProvider Formatter. (#60522)
14 май 2022, 19:41
Не верифицирован
14 май 2022, 19:41
1102b71
Код
Авторство
О чём код?
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. // See the LICENSE file in the project root for more information. #nullable disable using System.Collections.ObjectModel; using Microsoft.CodeAnalysis.CSharp.Symbols; using Microsoft.CodeAnalysis.ExpressionEvaluator; using Microsoft.CodeAnalysis.PooledObjects; using Type = Microsoft.VisualStudio.Debugger.Metadata.Type; namespace Microsoft.CodeAnalysis.CSharp.ExpressionEvaluator { internal sealed partial class CSharpFormatter : Formatter { public CSharpFormatter() : base(defaultFormat: "{{{0}}}", nullString: "null", thisString: "this") { } internal override bool IsValidIdentifier(string name) { return SyntaxFacts.IsValidIdentifier(name); } internal override bool IsIdentifierPartCharacter(char c) { return SyntaxFacts.IsIdentifierPartCharacter(c); } internal override bool IsPredefinedType(Type type) { return type.IsPredefinedType(); } internal override bool IsWhitespace(char c) { return SyntaxFacts.IsWhitespace(c); } // TODO: https://github.com/dotnet/roslyn/issues/37536 // This parsing is imprecise and may result in bad expressions. internal override string TrimAndGetFormatSpecifiers(string expression, out ReadOnlyCollection<string> formatSpecifiers) { expression = RemoveComments(expression); expression = RemoveFormatSpecifiers(expression, out formatSpecifiers); return RemoveLeadingAndTrailingContent(expression, 0, expression.Length, IsWhitespace, ch => ch == ';' || IsWhitespace(ch)); } internal override string GetOriginalLocalVariableName(string name) { if (!GeneratedNameParser.TryParseGeneratedName(name, out _, out var openBracketOffset, out var closeBracketOffset)) { return name; } var result = name.Substring(openBracketOffset + 1, closeBracketOffset - openBracketOffset - 1); return result; } internal override string GetOriginalFieldName(string name) { if (!GeneratedNameParser.TryParseGeneratedName(name, out _, out var openBracketOffset, out var closeBracketOffset)) { return name; } var result = name.Substring(openBracketOffset + 1, closeBracketOffset - openBracketOffset - 1); return result; } private static string RemoveComments(string expression) { var pooledBuilder = PooledStringBuilder.GetInstance(); var builder = pooledBuilder.Builder; var inMultilineComment = false; int length = expression.Length; // Workaround for https://dev.azure.com/devdiv/DevDiv/_workitems/edit/847849 // Do not remove any comments that might be in a string. // This won't work when there are quotes in the comment, but that's not that common. int lastQuote = expression.LastIndexOf('"') + 1; builder.Append(expression, 0, lastQuote); for (int i = lastQuote; i < length; i++) { var ch = expression[i]; if (inMultilineComment) { if (ch == '*' && i + 1 < length && expression[i + 1] == '/') { i++; inMultilineComment = false; } } else { if (ch == '/' && i + 1 < length) { var next = expression[i + 1]; if (next == '*') { i++; inMultilineComment = true; continue; } else if (next == '/') { // Ignore remainder of string. break; } } builder.Append(ch); } } if (builder.Length < length) { expression = builder.ToString(); } pooledBuilder.Free(); return expression; } } }