Browse Source

Merge branch 'master' of git://github.com/icsharpcode/ILSpy into Debugger

pull/191/merge
Eusebiu Marcu 15 years ago
parent
commit
dc66fbe25d
  1. 21
      ICSharpCode.Decompiler/Ast/AstBuilder.cs
  2. 2
      ICSharpCode.Decompiler/Ast/AstMethodBodyBuilder.cs
  3. 6
      ICSharpCode.Decompiler/Ast/NRefactoryExtensions.cs
  4. 7
      ICSharpCode.Decompiler/Ast/Transforms/ContextTrackingVisitor.cs
  5. 10
      ICSharpCode.Decompiler/Ast/Transforms/ConvertConstructorCallIntoInitializer.cs
  6. 1
      ICSharpCode.Decompiler/Ast/Transforms/DelegateConstruction.cs
  7. 37
      ICSharpCode.Decompiler/Ast/Transforms/PushNegation.cs
  8. 9
      ICSharpCode.Decompiler/Ast/Transforms/ReplaceMethodCallsWithOperators.cs
  9. 18
      ICSharpCode.Decompiler/Ast/Transforms/TransformationPipeline.cs
  10. 68
      ICSharpCode.Decompiler/Ast/Transforms/UsingStatementTransform.cs
  11. 1
      ICSharpCode.Decompiler/ICSharpCode.Decompiler.csproj
  12. 13
      ILSpy/CSharpLanguage.cs
  13. 4
      ILSpy/TreeNodes/ThreadedTreeNode.cs
  14. 44
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/AstComparer.cs
  15. 39
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/AstNode.cs
  16. 22
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/AstNodeCollection.cs
  17. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/AstType.cs
  18. 13
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/CSharpTokenNode.cs
  19. 7
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/CompilationUnit.cs
  20. 12
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/ComposedType.cs
  21. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/AnonymousMethodExpression.cs
  22. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ArgListExpression.cs
  23. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ArrayCreateExpression.cs
  24. 11
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ArrayInitializerExpression.cs
  25. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/AsExpression.cs
  26. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/AssignmentExpression.cs
  27. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/BaseReferenceExpression.cs
  28. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/BinaryOperatorExpression.cs
  29. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/CastExpression.cs
  30. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/CheckedExpression.cs
  31. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ConditionalExpression.cs
  32. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/DefaultValueExpression.cs
  33. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/DirectionExpression.cs
  34. 5
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/Expression.cs
  35. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/IdentifierExpression.cs
  36. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/IndexerExpression.cs
  37. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/InvocationExpression.cs
  38. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/IsExpression.cs
  39. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/LambdaExpression.cs
  40. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/MemberReferenceExpression.cs
  41. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/NamedArgumentExpression.cs
  42. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/NullReferenceExpression.cs
  43. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ObjectCreateExpression.cs
  44. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ParenthesizedExpression.cs
  45. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/PointerReferenceExpression.cs
  46. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/PrimitiveExpression.cs
  47. 23
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/QueryExpression.cs
  48. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/SizeOfExpression.cs
  49. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/StackAllocExpression.cs
  50. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ThisReferenceExpression.cs
  51. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/TypeOfExpression.cs
  52. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/TypeReferenceExpression.cs
  53. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/UnaryOperatorExpression.cs
  54. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/UncheckedExpression.cs
  55. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/Attribute.cs
  56. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/AttributeSection.cs
  57. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/Comment.cs
  58. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/Constraint.cs
  59. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/NamespaceDeclaration.cs
  60. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/TypeParameterDeclaration.cs
  61. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/UsingAliasDeclaration.cs
  62. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/UsingDeclaration.cs
  63. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Identifier.cs
  64. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/MemberType.cs
  65. 3
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/NodeType.cs
  66. 26
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/AnyNode.cs
  67. 28
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Backreference.cs
  68. 33
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Choice.cs
  69. 43
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Match.cs
  70. 29
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/NamedGroup.cs
  71. 42
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Pattern.cs
  72. 119
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Placeholder.cs
  73. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PrimitiveType.cs
  74. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/SimpleType.cs
  75. 11
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/BlockStatement.cs
  76. 10
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/BreakStatement.cs
  77. 17
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/ExpressionStatement.cs
  78. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/IfElseStatement.cs
  79. 10
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/Statement.cs
  80. 12
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/SwitchStatement.cs
  81. 12
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/TryCatchStatement.cs
  82. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/VariableDeclarationStatement.cs
  83. 9
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/Accessor.cs
  84. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/AttributedNode.cs
  85. 13
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/ConstructorDeclaration.cs
  86. 9
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/DestructorDeclaration.cs
  87. 6
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/ParameterDeclaration.cs
  88. 8
      NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/VariableInitializer.cs
  89. 10
      NRefactory/ICSharpCode.NRefactory/CSharp/OutputVisitor/OutputVisitor.cs
  90. 9
      NRefactory/ICSharpCode.NRefactory/ICSharpCode.NRefactory.csproj

21
ICSharpCode.Decompiler/Ast/AstBuilder.cs

@ -3,6 +3,7 @@ using System.Collections.Generic; @@ -3,6 +3,7 @@ using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Threading;
using Decompiler.Transforms;
using ICSharpCode.Decompiler;
using ICSharpCode.NRefactory.CSharp;
using Mono.Cecil;
@ -24,14 +25,25 @@ namespace Decompiler @@ -24,14 +25,25 @@ namespace Decompiler
this.context = context;
}
public static bool MemberIsHidden(MemberReference member)
{
MethodDefinition method = member as MethodDefinition;
if (method != null && (method.IsGetter || method.IsSetter || method.IsAddOn || method.IsRemoveOn))
return true;
TypeDefinition type = member as TypeDefinition;
if (type != null && type.DeclaringType != null && type.Name.StartsWith("<>c__DisplayClass", StringComparison.Ordinal) && type.IsCompilerGenerated())
return true;
return false;
}
public void GenerateCode(ITextOutput output)
{
GenerateCode(output, null);
}
public void GenerateCode(ITextOutput output, Predicate<IAstVisitor<object, object>> transformAbortCondition)
public void GenerateCode(ITextOutput output, Predicate<IAstTransform> transformAbortCondition)
{
Transforms.TransformationPipeline.RunTransformationsUntil(astCompileUnit, transformAbortCondition, context);
TransformationPipeline.RunTransformationsUntil(astCompileUnit, transformAbortCondition, context);
astCompileUnit.AcceptVisitor(new InsertParenthesesVisitor { InsertParenthesesForReadability = true }, null);
var outputFormatter = new TextOutputFormatter(output);
@ -139,6 +151,8 @@ namespace Decompiler @@ -139,6 +151,8 @@ namespace Decompiler
// Nested types
foreach(TypeDefinition nestedTypeDef in typeDef.NestedTypes) {
if (MemberIsHidden(nestedTypeDef))
continue;
astType.AddChild(CreateType(nestedTypeDef), TypeDeclaration.MemberRole);
}
@ -423,7 +437,7 @@ namespace Decompiler @@ -423,7 +437,7 @@ namespace Decompiler
// Add methods
foreach(MethodDefinition methodDef in typeDef.Methods) {
if (methodDef.IsSpecialName) continue;
if (methodDef.IsConstructor || MemberIsHidden(methodDef)) continue;
astType.AddChild(CreateMethod(methodDef), TypeDeclaration.MemberRole);
}
@ -460,6 +474,7 @@ namespace Decompiler @@ -460,6 +474,7 @@ namespace Decompiler
// don't show visibility for static ctors
astMethod.Modifiers &= ~Modifiers.VisibilityMask;
}
astMethod.Name = methodDef.DeclaringType.Name;
astMethod.Parameters.AddRange(MakeParameters(methodDef.Parameters));
astMethod.Body = AstMethodBodyBuilder.CreateMethodBody(methodDef, context);
return astMethod;

2
ICSharpCode.Decompiler/Ast/AstMethodBodyBuilder.cs

@ -501,7 +501,7 @@ namespace Decompiler @@ -501,7 +501,7 @@ namespace Decompiler
case Code.Endfinally: return null;
case Code.Initblk: throw new NotImplementedException();
case Code.Initobj: throw new NotImplementedException();
case Code.Isinst: return arg1.IsType(AstBuilder.ConvertType((Cecil.TypeReference)operand));
case Code.Isinst: return arg1.CastAs(AstBuilder.ConvertType((Cecil.TypeReference)operand));
case Code.Jmp: throw new NotImplementedException();
case Code.Ldarg:
if (methodDef.HasThis && ((ParameterDefinition)operand).Index < 0) {

6
ICSharpCode.Decompiler/Ast/NRefactoryExtensions.cs

@ -14,5 +14,11 @@ namespace Decompiler @@ -14,5 +14,11 @@ namespace Decompiler
node.AddAnnotation(annotation);
return node;
}
public static T Detach<T>(this T node) where T : AstNode
{
node.Remove();
return node;
}
}
}

7
ICSharpCode.Decompiler/Ast/Transforms/ContextTrackingVisitor.cs

@ -11,7 +11,7 @@ namespace Decompiler.Transforms @@ -11,7 +11,7 @@ namespace Decompiler.Transforms
/// <summary>
/// Base class for AST visitors that need the current type/method context info.
/// </summary>
public abstract class ContextTrackingVisitor : DepthFirstAstVisitor<object, object>
public abstract class ContextTrackingVisitor : DepthFirstAstVisitor<object, object>, IAstTransform
{
protected readonly DecompilerContext context;
@ -65,5 +65,10 @@ namespace Decompiler.Transforms @@ -65,5 +65,10 @@ namespace Decompiler.Transforms
context.CurrentMethod = null;
}
}
void IAstTransform.Run(AstNode node)
{
node.AcceptVisitor(this, null);
}
}
}

10
ICSharpCode.Decompiler/Ast/Transforms/ConvertConstructorCallIntoInitializer.cs

@ -8,7 +8,10 @@ using Mono.Cecil; @@ -8,7 +8,10 @@ using Mono.Cecil;
namespace Decompiler.Transforms
{
public class ConvertConstructorCallIntoInitializer : DepthFirstAstVisitor<object, object>
/// <summary>
/// If the first element of a constructor is a chained constructor call, convert it into a constructor initializer.
/// </summary>
public class ConvertConstructorCallIntoInitializer : DepthFirstAstVisitor<object, object>, IAstTransform
{
public override object VisitConstructorDeclaration(ConstructorDeclaration constructorDeclaration, object data)
{
@ -51,5 +54,10 @@ namespace Decompiler.Transforms @@ -51,5 +54,10 @@ namespace Decompiler.Transforms
}
return null;
}
void IAstTransform.Run(AstNode node)
{
node.AcceptVisitor(this, null);
}
}
}

1
ICSharpCode.Decompiler/Ast/Transforms/DelegateConstruction.cs

@ -14,6 +14,7 @@ namespace Decompiler.Transforms @@ -14,6 +14,7 @@ namespace Decompiler.Transforms
/// <summary>
/// Converts "new Action(obj, ldftn(func))" into "new Action(obj.func)".
/// For anonymous methods, creates an AnonymousMethodExpression.
/// Also gets rid of any "Display Classes" left over after inlining an anonymous method.
/// </summary>
public class DelegateConstruction : ContextTrackingVisitor
{

37
ICSharpCode.Decompiler/Ast/Transforms/PushNegation.cs

@ -1,11 +1,12 @@ @@ -1,11 +1,12 @@
using System;
using System.Collections.Generic;
using System.Linq;
using ICSharpCode.NRefactory.CSharp;
using ICSharpCode.NRefactory.CSharp.PatternMatching;
namespace Decompiler.Transforms
{
public class PushNegation: DepthFirstAstVisitor<object, object>
public class PushNegation: DepthFirstAstVisitor<object, object>, IAstTransform
{
public override object VisitUnaryOperatorExpression(UnaryOperatorExpression unary, object data)
{
@ -75,6 +76,18 @@ namespace Decompiler.Transforms @@ -75,6 +76,18 @@ namespace Decompiler.Transforms
return base.VisitUnaryOperatorExpression(unary, data);
}
readonly static AstNode asCastIsNullPattern = new BinaryOperatorExpression(
new AnyNode("expr").ToExpression().CastAs(new AnyNode("type").ToType()),
BinaryOperatorType.Equality,
new NullReferenceExpression()
);
readonly static AstNode asCastIsNotNullPattern = new BinaryOperatorExpression(
new AnyNode("expr").ToExpression().CastAs(new AnyNode("type").ToType()),
BinaryOperatorType.InEquality,
new NullReferenceExpression()
);
public override object VisitBinaryOperatorExpression(BinaryOperatorExpression binaryOperatorExpression, object data)
{
BinaryOperatorType op = binaryOperatorExpression.Operator;
@ -94,8 +107,26 @@ namespace Decompiler.Transforms @@ -94,8 +107,26 @@ namespace Decompiler.Transforms
binaryOperatorExpression.ReplaceWith(uoe);
return uoe.AcceptVisitor(this, data);
} else {
return base.VisitBinaryOperatorExpression(binaryOperatorExpression, data);
bool negate = false;
Match m = asCastIsNotNullPattern.Match(binaryOperatorExpression);
if (m == null) {
m = asCastIsNullPattern.Match(binaryOperatorExpression);
negate = true;
}
if (m != null) {
Expression expr = ((Expression)m["expr"].Single()).Detach().IsType((AstType)m["type"].Single().Detach());
if (negate)
expr = new UnaryOperatorExpression(UnaryOperatorType.Not, expr);
binaryOperatorExpression.ReplaceWith(expr);
return expr.AcceptVisitor(this, data);
} else {
return base.VisitBinaryOperatorExpression(binaryOperatorExpression, data);
}
}
}
void IAstTransform.Run(AstNode node)
{
node.AcceptVisitor(this, null);
}
}
}

9
ICSharpCode.Decompiler/Ast/Transforms/ReplaceMethodCallsWithOperators.cs

@ -11,7 +11,7 @@ namespace Decompiler.Transforms @@ -11,7 +11,7 @@ namespace Decompiler.Transforms
/// Replaces method calls with the appropriate operator expressions.
/// Also simplifies "x = x op y" into "x op= y" where possible.
/// </summary>
public class ReplaceMethodCallsWithOperators : DepthFirstAstVisitor<object, object>
public class ReplaceMethodCallsWithOperators : DepthFirstAstVisitor<object, object>, IAstTransform
{
public override object VisitInvocationExpression(InvocationExpression invocationExpression, object data)
{
@ -145,7 +145,7 @@ namespace Decompiler.Transforms @@ -145,7 +145,7 @@ namespace Decompiler.Transforms
// First, combine "x = x op y" into "x op= y"
BinaryOperatorExpression binary = assignment.Right as BinaryOperatorExpression;
if (binary != null && assignment.Operator == AssignmentOperatorType.Assign) {
if (IsWithoutSideEffects(assignment.Left) && AstComparer.AreEqual(assignment.Left, binary.Left) == true) {
if (IsWithoutSideEffects(assignment.Left) && assignment.Left.Match(binary.Left) != null) {
switch (binary.Operator) {
case BinaryOperatorType.Add:
assignment.Operator = AssignmentOperatorType.Add;
@ -191,5 +191,10 @@ namespace Decompiler.Transforms @@ -191,5 +191,10 @@ namespace Decompiler.Transforms
{
return left is IdentifierExpression; // TODO
}
void IAstTransform.Run(AstNode node)
{
node.AcceptVisitor(this, null);
}
}
}

18
ICSharpCode.Decompiler/Ast/Transforms/TransformationPipeline.cs

@ -7,19 +7,25 @@ using ICSharpCode.NRefactory.CSharp; @@ -7,19 +7,25 @@ using ICSharpCode.NRefactory.CSharp;
namespace Decompiler.Transforms
{
public interface IAstTransform
{
void Run(AstNode node);
}
public static class TransformationPipeline
{
public static IAstVisitor<object, object>[] CreatePipeline(DecompilerContext context)
public static IAstTransform[] CreatePipeline(DecompilerContext context)
{
return new IAstVisitor<object, object>[] {
return new IAstTransform[] {
new PushNegation(),
new DelegateConstruction(context),
new UsingStatementTransform(),
new ConvertConstructorCallIntoInitializer(),
new ReplaceMethodCallsWithOperators(),
};
}
public static void RunTransformationsUntil(AstNode node, Predicate<IAstVisitor<object, object>> abortCondition, DecompilerContext context)
public static void RunTransformationsUntil(AstNode node, Predicate<IAstTransform> abortCondition, DecompilerContext context)
{
if (node == null)
return;
@ -37,11 +43,11 @@ namespace Decompiler.Transforms @@ -37,11 +43,11 @@ namespace Decompiler.Transforms
}
}
foreach (var visitor in CreatePipeline(context)) {
foreach (var transform in CreatePipeline(context)) {
context.CancellationToken.ThrowIfCancellationRequested();
if (abortCondition != null && abortCondition(visitor))
if (abortCondition != null && abortCondition(transform))
return;
node.AcceptVisitor(visitor, null);
transform.Run(node);
}
}
}

68
ICSharpCode.Decompiler/Ast/Transforms/UsingStatementTransform.cs

@ -0,0 +1,68 @@ @@ -0,0 +1,68 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
using System.Linq;
using Decompiler.Transforms;
using ICSharpCode.NRefactory.CSharp;
using ICSharpCode.NRefactory.CSharp.PatternMatching;
namespace Decompiler.Transforms
{
/// <summary>
/// Finds the expanded form of using statements using pattern matching and replaces it with a UsingStatement.
/// </summary>
public class UsingStatementTransform : IAstTransform
{
static readonly AstNode usingVarDeclPattern = new VariableDeclarationStatement {
Type = new AnyNode("type").ToType(),
Variables = {
new NamedNode(
"variable",
new VariableInitializer {
Initializer = new AnyNode().ToExpression()
}
).ToVariable()
}
};
static readonly AstNode usingTryCatchPattern = new TryCatchStatement {
TryBlock = new AnyNode("body").ToBlock(),
FinallyBlock = new BlockStatement {
Statements = {
new IfElseStatement {
Condition = new BinaryOperatorExpression(
new NamedNode("ident", new IdentifierExpression()).ToExpression(),
BinaryOperatorType.InEquality,
new NullReferenceExpression()
),
TrueStatement = new BlockStatement {
Statements = {
new ExpressionStatement(new Backreference("ident").ToExpression().Invoke("Dispose"))
}
}
}
}
}
};
public void Run(AstNode compilationUnit)
{
foreach (AstNode node in compilationUnit.Descendants.ToArray()) {
Match m1 = usingVarDeclPattern.Match(node);
if (m1 == null) continue;
Match m2 = usingTryCatchPattern.Match(node.NextSibling);
if (m2 == null) continue;
if (((VariableInitializer)m1["variable"].Single()).Name == ((IdentifierExpression)m2["ident"].Single()).Identifier) {
BlockStatement body = (BlockStatement)m2["body"].Single();
body.Remove();
node.NextSibling.Remove();
node.ReplaceWith(
varDecl => new UsingStatement {
ResourceAcquisition = varDecl,
EmbeddedStatement = body
});
}
}
}
}
}

1
ICSharpCode.Decompiler/ICSharpCode.Decompiler.csproj

@ -67,6 +67,7 @@ @@ -67,6 +67,7 @@
<Compile Include="Ast\Transforms\RemoveGotos.cs" />
<Compile Include="Ast\Transforms\RestoreLoop.cs" />
<Compile Include="Ast\Transforms\TransformationPipeline.cs" />
<Compile Include="Ast\Transforms\UsingStatementTransform.cs" />
<Compile Include="CecilExtensions.cs" />
<Compile Include="CodeMappings.cs" />
<Compile Include="DecompilerException.cs" />

13
ILSpy/CSharpLanguage.cs

@ -36,7 +36,7 @@ namespace ICSharpCode.ILSpy @@ -36,7 +36,7 @@ namespace ICSharpCode.ILSpy
{
string name = "C#";
bool showAllMembers;
Predicate<IAstVisitor<object, object>> transformAbortCondition = null;
Predicate<IAstTransform> transformAbortCondition = null;
public CSharpLanguage()
{
@ -167,16 +167,7 @@ namespace ICSharpCode.ILSpy @@ -167,16 +167,7 @@ namespace ICSharpCode.ILSpy
public override bool ShowMember(MemberReference member)
{
if (showAllMembers) {
return true;
}
MethodDefinition method = member as MethodDefinition;
if (method != null && (method.IsGetter || method.IsSetter || method.IsAddOn || method.IsRemoveOn))
return false;
TypeDefinition type = member as TypeDefinition;
if (type != null && type.Name.StartsWith("<>c__DisplayClass", StringComparison.Ordinal) && type.IsCompilerGenerated())
return false;
return true;
return showAllMembers || !AstBuilder.MemberIsHidden(member);
}
}
}

4
ILSpy/TreeNodes/ThreadedTreeNode.cs

@ -50,8 +50,8 @@ namespace ICSharpCode.ILSpy.TreeNodes @@ -50,8 +50,8 @@ namespace ICSharpCode.ILSpy.TreeNodes
result.Add(child);
App.Current.Dispatcher.BeginInvoke(DispatcherPriority.Normal, new Action<ILSpyTreeNode>(
delegate (ILSpyTreeNode newChild) {
// don't access "child" here the background thread might already be running
// the next loop iteration
// don't access "child" here the
// background thread might already be running the next loop iteration
if (loadChildrenTask == thisTask) {
this.Children.Insert(this.Children.Count - 1, newChild);
}

44
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/AstComparer.cs

@ -1,44 +0,0 @@ @@ -1,44 +0,0 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
using System.Collections.Generic;
namespace ICSharpCode.NRefactory.CSharp
{
/// <summary>
/// Compares whether two ASTs are structurally identical.
/// </summary>
public static class AstComparer
{
static HashSet<Type> nodeTypesWithoutExtraInfo = new HashSet<Type> {
typeof(IdentifierExpression)
};
public static bool? AreEqual(AstNode node1, AstNode node2)
{
if (node1 == node2)
return true;
if (node1 == null || node1.IsNull || node2 == null || node2.IsNull)
return false;
Type nodeType = node1.GetType();
if (nodeType != node2.GetType())
return false;
if (node1.Role != node2.Role)
return false;
AstNode child1 = node1.FirstChild;
AstNode child2 = node2.FirstChild;
bool? result = true;
while (result != false && (child1 != null || child2 != null)) {
result &= AreEqual(child1, child2);
child1 = child1.NextSibling;
child2 = child2.NextSibling;
}
if (nodeTypesWithoutExtraInfo.Contains(nodeType))
return result;
if (nodeType == typeof(Identifier))
return ((Identifier)node1).Name == ((Identifier)node2).Name;
return null;
}
}
}

39
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/AstNode.cs

@ -25,11 +25,14 @@ @@ -25,11 +25,14 @@
// THE SOFTWARE.
using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Threading;
using ICSharpCode.NRefactory.CSharp.PatternMatching;
namespace ICSharpCode.NRefactory.CSharp
{
public abstract class AstNode
@ -55,6 +58,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -55,6 +58,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return default (S);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
return other == null || other.IsNull;
}
}
#endregion
@ -569,6 +577,37 @@ namespace ICSharpCode.NRefactory.CSharp @@ -569,6 +577,37 @@ namespace ICSharpCode.NRefactory.CSharp
public abstract S AcceptVisitor<T, S> (IAstVisitor<T, S> visitor, T data);
#region Pattern Matching
/// <summary>
/// Performs a pattern matching operation.
/// <c>this</c> is the pattern, <paramref name="other"/> is the AST that is being matched.
/// </summary>
/// <returns>
/// If successful, a match object containing the matched groups.
/// If the match failed, returns <c>null</c>.
/// </returns>
/// <remarks>
/// Patterns are ASTs that contain special pattern nodes (from the PatternMatching namespace).
/// However, it is also possible to match two ASTs without any pattern nodes - doing so will produce an empty match object
/// if the two ASTs are structurally identical; or will return <c>null</c> if the ASTs are not identical.
/// </remarks>
public Match Match(AstNode other)
{
Match match = new Match();
if (DoMatch(other, match))
return match;
else
return null;
}
protected static bool MatchString(string name1, string name2)
{
return string.IsNullOrEmpty(name1) || name1 == name2;
}
protected internal abstract bool DoMatch(AstNode other, Match match);
#endregion
// the Root role must be available when creating the null nodes, so we can't put it in the Roles class
static readonly Role<AstNode> RootRole = new Role<AstNode>("Root");

22
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/AstNodeCollection.cs

@ -5,13 +5,14 @@ using System; @@ -5,13 +5,14 @@ using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using ICSharpCode.NRefactory.CSharp.PatternMatching;
namespace ICSharpCode.NRefactory.CSharp
{
/// <summary>
/// Represents the children of an AstNode that have a specific role.
/// </summary>
public struct AstNodeCollection<T> : ICollection<T> where T : AstNode
public class AstNodeCollection<T> : ICollection<T> where T : AstNode
{
readonly AstNode node;
readonly Role<T> role;
@ -152,5 +153,24 @@ namespace ICSharpCode.NRefactory.CSharp @@ -152,5 +153,24 @@ namespace ICSharpCode.NRefactory.CSharp
return !(left.role == right.role && left.node == right.node);
}
#endregion
internal bool DoMatch(AstNodeCollection<T> other, Match match)
{
AstNode cur1 = this.node.FirstChild;
AstNode cur2 = other.node.FirstChild;
while (true) {
while (cur1 != null && cur1.Role != role)
cur1 = cur1.NextSibling;
while (cur2 != null && cur2.Role != role)
cur2 = cur2.NextSibling;
if (cur1 == null || cur2 == null)
break;
if (!cur1.DoMatch(cur2, match))
return false;
cur1 = cur1.NextSibling;
cur2 = cur2.NextSibling;
}
return cur1 == null && cur2 == null;
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/AstType.cs

@ -1,4 +1,5 @@ @@ -1,4 +1,5 @@
using System;
using System.Collections.Generic;
namespace ICSharpCode.NRefactory.CSharp
{
@ -22,6 +23,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -22,6 +23,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return default (S);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
return other == null || other.IsNull;
}
}
#endregion

13
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/CSharpTokenNode.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// TokenNode.cs
//
// Author:
@ -46,6 +46,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -46,6 +46,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return default (S);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
return other == null || other.IsNull;
}
}
@ -80,6 +85,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -80,6 +85,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitCSharpTokenNode (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
CSharpTokenNode o = other as CSharpTokenNode;
return o != null;
}
public override string ToString ()
{
return string.Format ("[CSharpTokenNode: StartLocation={0}, EndLocation={1}, Role={2}]", StartLocation, EndLocation, Role);

7
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/CompilationUnit.cs

@ -42,6 +42,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -42,6 +42,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
CompilationUnit o = other as CompilationUnit;
return o != null && GetChildrenByRole(MemberRole).DoMatch(o.GetChildrenByRole(MemberRole), match);
}
public AstNode GetNodeAt (int line, int column)
{
return GetNodeAt (new AstLocation (line, column));
@ -99,7 +105,6 @@ namespace ICSharpCode.NRefactory.CSharp @@ -99,7 +105,6 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitCompilationUnit (this, data);
}
}
}

12
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/ComposedType.cs

@ -76,6 +76,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -76,6 +76,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitComposedType (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ComposedType o = other as ComposedType;
return o != null && this.HasNullableSpecifier == o.HasNullableSpecifier && this.PointerRank == o.PointerRank && this.ArraySpecifiers.DoMatch(o.ArraySpecifiers, match);
}
public override string ToString()
{
StringBuilder b = new StringBuilder();
@ -156,6 +162,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -156,6 +162,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitArraySpecifier(this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ArraySpecifier o = other as ArraySpecifier;
return o != null && this.Dimensions == o.Dimensions;
}
public override string ToString()
{
return "[" + new string(',', this.Dimensions - 1) + "]";

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/AnonymousMethodExpression.cs

@ -64,5 +64,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -64,5 +64,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitAnonymousMethodExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
AnonymousMethodExpression o = other as AnonymousMethodExpression;
return o != null && this.HasParameterList == o.HasParameterList && this.Parameters.DoMatch(o.Parameters, match) && this.Body.DoMatch(o.Body, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ArgListExpression.cs

@ -57,6 +57,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -57,6 +57,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitArgListExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ArgListExpression o = other as ArgListExpression;
return o != null && this.IsAccess == o.IsAccess && this.Arguments.DoMatch(o.Arguments, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ArrayCreateExpression.cs

@ -37,5 +37,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -37,5 +37,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitArrayCreateExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ArrayCreateExpression o = other as ArrayCreateExpression;
return o != null && this.Type.DoMatch(o.Type, match) && this.Arguments.DoMatch(o.Arguments, match) && this.Initializer.DoMatch(o.Initializer, match);
}
}
}

11
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ArrayInitializerExpression.cs

@ -48,6 +48,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -48,6 +48,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return default (S);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
return other == null || other.IsNull;
}
}
#endregion
@ -67,6 +72,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -67,6 +72,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitArrayInitializerExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ArrayInitializerExpression o = other as ArrayInitializerExpression;
return o != null && this.Elements.DoMatch(o.Elements, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/AsExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// AsExpression.cs
//
// Author:
@ -49,6 +49,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -49,6 +49,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitAsExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
AsExpression o = other as AsExpression;
return o != null && this.Expression.DoMatch(o.Expression, match) && this.Type.DoMatch(o.Type, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/AssignmentExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// AssignmentExpression.cs
//
// Author:
@ -72,6 +72,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -72,6 +72,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitAssignmentExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
AssignmentExpression o = other as AssignmentExpression;
return o != null && this.Left.DoMatch(o.Left, match) && this.Operator == o.Operator && this.Right.DoMatch(o.Right, match);
}
public static string GetOperatorSymbol(AssignmentOperatorType op)
{
switch (op) {

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/BaseReferenceExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// BaseReferenceExpression.cs
//
// Author:
@ -51,5 +51,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -51,5 +51,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitBaseReferenceExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
BaseReferenceExpression o = other as BaseReferenceExpression;
return o != null;
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/BinaryOperatorExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// BinaryOperatorExpression.cs
//
// Author:
@ -72,6 +72,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -72,6 +72,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitBinaryOperatorExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
BinaryOperatorExpression o = other as BinaryOperatorExpression;
return o != null && this.Left.DoMatch(o.Left, match) && this.Operator == o.Operator && this.Right.DoMatch(o.Right, match);
}
public static string GetOperatorSymbol(BinaryOperatorType op)
{
switch (op) {

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/CastExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// CastExpression.cs
//
// Author:
@ -53,6 +53,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -53,6 +53,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitCastExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
CastExpression o = other as CastExpression;
return o != null && this.Type.DoMatch(o.Type, match) && this.Expression.DoMatch(o.Expression, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/CheckedExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// CheckedExpression.cs
//
// Author:
@ -52,5 +52,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -52,5 +52,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitCheckedExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
CheckedExpression o = other as CheckedExpression;
return o != null && this.Expression.DoMatch(o.Expression, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ConditionalExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// ConditionalExpression.cs
//
// Author:
@ -64,5 +64,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -64,5 +64,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitConditionalExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ConditionalExpression o = other as ConditionalExpression;
return o != null && this.Condition.DoMatch(o.Condition, match) && this.TrueExpression.DoMatch(o.TrueExpression, match) && this.FalseExpression.DoMatch(o.FalseExpression, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/DefaultValueExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// DefaultValueExpression.cs
//
// Author:
@ -52,6 +52,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -52,6 +52,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitDefaultValueExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
DefaultValueExpression o = other as DefaultValueExpression;
return o != null && this.Type.DoMatch(o.Type, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/DirectionExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// DirectionExpression.cs
//
// Author:
@ -56,5 +56,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -56,5 +56,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitDirectionExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
DirectionExpression o = other as DirectionExpression;
return o != null && this.FieldDirection == o.FieldDirection && this.Expression.DoMatch(o.Expression, match);
}
}
}

5
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/Expression.cs

@ -31,6 +31,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -31,6 +31,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return default (S);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
return other == null || other.IsNull;
}
}
#endregion

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/IdentifierExpression.cs

@ -64,5 +64,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -64,5 +64,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitIdentifierExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
IdentifierExpression o = other as IdentifierExpression;
return o != null && MatchString(this.Identifier, o.Identifier) && this.TypeArguments.DoMatch(o.TypeArguments, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/IndexerExpression.cs

@ -54,5 +54,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -54,5 +54,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitIndexerExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
IndexerExpression o = other as IndexerExpression;
return o != null && this.Target.DoMatch(o.Target, match) && this.Arguments.DoMatch(o.Arguments, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/InvocationExpression.cs

@ -54,5 +54,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -54,5 +54,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitInvocationExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
InvocationExpression o = other as InvocationExpression;
return o != null && this.Target.DoMatch(o.Target, match) && this.Arguments.DoMatch(o.Arguments, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/IsExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// TypeOfIsExpression.cs
//
// Author:
@ -49,6 +49,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -49,6 +49,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitIsExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
IsExpression o = other as IsExpression;
return o != null && this.Expression.DoMatch(o.Expression, match) && this.Type.DoMatch(o.Type, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/LambdaExpression.cs

@ -53,5 +53,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -53,5 +53,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitLambdaExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
LambdaExpression o = other as LambdaExpression;
return o != null && this.Parameters.DoMatch(o.Parameters, match) && this.Body.DoMatch(o.Body, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/MemberReferenceExpression.cs

@ -63,5 +63,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -63,5 +63,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitMemberReferenceExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
MemberReferenceExpression o = other as MemberReferenceExpression;
return o != null && this.Target.DoMatch(o.Target, match) && MatchString(this.MemberName, o.MemberName) && this.TypeArguments.DoMatch(o.TypeArguments, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/NamedArgumentExpression.cs

@ -28,5 +28,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -28,5 +28,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitNamedArgumentExpression(this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
NamedArgumentExpression o = other as NamedArgumentExpression;
return o != null && MatchString(this.Identifier, o.Identifier) && this.Expression.DoMatch(o.Expression, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/NullReferenceExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// NullReferenceExpression.cs
//
// Author:
@ -35,5 +35,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -35,5 +35,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitNullReferenceExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
NullReferenceExpression o = other as NullReferenceExpression;
return o != null;
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ObjectCreateExpression.cs

@ -65,5 +65,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -65,5 +65,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitObjectCreateExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ObjectCreateExpression o = other as ObjectCreateExpression;
return o != null && this.Type.DoMatch(o.Type, match) && this.Arguments.DoMatch(o.Arguments, match) && this.Initializer.DoMatch(o.Initializer, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ParenthesizedExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// ParenthesizedExpression.cs
//
// Author:
@ -48,5 +48,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -48,5 +48,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitParenthesizedExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ParenthesizedExpression o = other as ParenthesizedExpression;
return o != null && this.Expression.DoMatch(o.Expression, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/PointerReferenceExpression.cs

@ -57,5 +57,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -57,5 +57,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitPointerReferenceExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
PointerReferenceExpression o = other as PointerReferenceExpression;
return o != null && MatchString(this.MemberName, o.MemberName) && this.TypeArguments.DoMatch(o.TypeArguments, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/PrimitiveExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// PrimitiveExpression.cs
//
// Author:
@ -66,5 +66,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -66,5 +66,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitPrimitiveExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
PrimitiveExpression o = other as PrimitiveExpression;
return o != null && object.Equals(this.Value, o.Value);
}
}
}

23
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/QueryExpression.cs

@ -25,6 +25,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -25,6 +25,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return default (S);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
return other == null || other.IsNull;
}
}
#endregion
@ -36,6 +41,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -36,6 +41,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitQueryExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
QueryExpression o = other as QueryExpression;
return o != null && this.Clauses.DoMatch(o.Clauses, match);
}
}
public abstract class QueryClause : AstNode
@ -43,6 +54,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -43,6 +54,12 @@ namespace ICSharpCode.NRefactory.CSharp
public override NodeType NodeType {
get { return NodeType.QueryClause; }
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
QueryClause o = other as QueryClause;
throw new NotImplementedException();
}
}
/// <summary>
@ -293,6 +310,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -293,6 +310,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitQueryOrdering (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
QueryOrdering o = other as QueryOrdering;
return o != null && this.Direction == o.Direction && this.Expression.DoMatch(o.Expression, match);
}
}
public enum QueryOrderingDirection

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/SizeOfExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// SizeOfExpression.cs
//
// Author:
@ -52,5 +52,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -52,5 +52,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitSizeOfExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
SizeOfExpression o = other as SizeOfExpression;
return o != null && this.Type.DoMatch(o.Type, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/StackAllocExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// StackAllocExpression.cs
//
// Author:
@ -57,5 +57,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -57,5 +57,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitStackAllocExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
StackAllocExpression o = other as StackAllocExpression;
return o != null && this.Type.DoMatch(o.Type, match) && this.CountExpression.DoMatch(o.CountExpression, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/ThisReferenceExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// ThisReferenceExpression.cs
//
// Author:
@ -51,5 +51,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -51,5 +51,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitThisReferenceExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ThisReferenceExpression o = other as ThisReferenceExpression;
return o != null;
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/TypeOfExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// TypeOfExpression.cs
//
// Author:
@ -53,5 +53,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -53,5 +53,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitTypeOfExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
TypeOfExpression o = other as TypeOfExpression;
return o != null && this.Type.DoMatch(o.Type, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/TypeReferenceExpression.cs

@ -20,5 +20,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -20,5 +20,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitTypeReferenceExpression(this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
TypeReferenceExpression o = other as TypeReferenceExpression;
return o != null && this.Type.DoMatch(o.Type, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/UnaryOperatorExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// UnaryOperatorExpression.cs
//
// Author:
@ -64,6 +64,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -64,6 +64,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitUnaryOperatorExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
UnaryOperatorExpression o = other as UnaryOperatorExpression;
return o != null && this.Operator == o.Operator && this.Expression.DoMatch(o.Expression, match);
}
public static string GetOperatorSymbol(UnaryOperatorType op)
{
switch (op) {

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Expressions/UncheckedExpression.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// UncheckedExpression.cs
//
// Author:
@ -52,5 +52,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -52,5 +52,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitUncheckedExpression (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
UncheckedExpression o = other as UncheckedExpression;
return o != null && this.Expression.DoMatch(o.Expression, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/Attribute.cs

@ -52,5 +52,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -52,5 +52,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitAttribute (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
Attribute o = other as Attribute;
return o != null && this.Type.DoMatch(o.Type, match) && this.Arguments.DoMatch(o.Arguments, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/AttributeSection.cs

@ -58,6 +58,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -58,6 +58,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitAttributeSection (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
AttributeSection o = other as AttributeSection;
return o != null && this.AttributeTarget == o.AttributeTarget && this.Attributes.DoMatch(o.Attributes, match);
}
public static string GetAttributeTargetName(AttributeTarget attributeTarget)
{
switch (attributeTarget) {

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/Comment.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// Comment.cs
//
// Author:
@ -86,6 +86,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -86,6 +86,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitComment (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
Comment o = other as Comment;
return o != null && this.CommentType == o.CommentType && MatchString(this.Content, o.Content);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/Constraint.cs

@ -61,6 +61,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -61,6 +61,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitConstraint (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
Constraint o = other as Constraint;
return o != null && MatchString(this.TypeParameter, o.TypeParameter) && this.BaseTypes.DoMatch(o.BaseTypes, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/NamespaceDeclaration.cs

@ -100,5 +100,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -100,5 +100,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitNamespaceDeclaration (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
NamespaceDeclaration o = other as NamespaceDeclaration;
return o != null && MatchString(this.Name, o.Name) && this.Members.DoMatch(o.Members, match);
}
}
};

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/TypeParameterDeclaration.cs

@ -38,5 +38,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -38,5 +38,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitTypeParameterDeclaration(this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
TypeParameterDeclaration o = other as TypeParameterDeclaration;
return o != null && this.Variance == o.Variance && MatchString(this.Name, o.Name);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/UsingAliasDeclaration.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// UsingAliasDeclaration.cs
//
// Author:
@ -70,5 +70,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -70,5 +70,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitUsingAliasDeclaration (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
UsingAliasDeclaration o = other as UsingAliasDeclaration;
return o != null && MatchString(this.Alias, o.Alias) && this.Import.DoMatch(o.Import, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/GeneralScope/UsingDeclaration.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// UsingDeclaration.cs
//
// Author:
@ -64,5 +64,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -64,5 +64,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitUsingDeclaration (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
UsingDeclaration o = other as UsingDeclaration;
return o != null && this.Import.DoMatch(o.Import, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Identifier.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// Identifier.cs
//
// Author:
@ -91,5 +91,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -91,5 +91,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitIdentifier (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
Identifier o = other as Identifier;
return o != null && MatchString(this.Name, o.Name);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/MemberType.cs

@ -60,6 +60,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -60,6 +60,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitMemberType (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
MemberType o = other as MemberType;
return o != null && this.IsDoubleColon == o.IsDoubleColon && MatchString(this.MemberName, o.MemberName) && this.Target.DoMatch(o.Target, match);
}
public override string ToString()
{
StringBuilder b = new StringBuilder();

3
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/NodeType.cs

@ -43,7 +43,8 @@ namespace ICSharpCode.NRefactory.CSharp @@ -43,7 +43,8 @@ namespace ICSharpCode.NRefactory.CSharp
Statement,
Expression,
Token,
QueryClause
QueryClause,
Pattern
}
}

26
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/AnyNode.cs

@ -0,0 +1,26 @@ @@ -0,0 +1,26 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
namespace ICSharpCode.NRefactory.CSharp.PatternMatching
{
/// <summary>
/// Matches any node.
/// </summary>
public class AnyNode : Pattern
{
readonly string groupName;
public AnyNode(string groupName = null)
{
this.groupName = groupName;
}
protected internal override bool DoMatch(AstNode other, Match match)
{
match.Add(this.groupName, other);
return other != null && !other.IsNull;
}
}
}

28
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Backreference.cs

@ -0,0 +1,28 @@ @@ -0,0 +1,28 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
using System.Linq;
namespace ICSharpCode.NRefactory.CSharp.PatternMatching
{
/// <summary>
/// Matches the last entry in the specified named group.
/// </summary>
public class Backreference : Pattern
{
readonly string referencedGroupName;
public Backreference(string referencedGroupName)
{
if (referencedGroupName == null)
throw new ArgumentNullException("referencedGroupName");
this.referencedGroupName = referencedGroupName;
}
protected internal override bool DoMatch(AstNode other, Match match)
{
return match[referencedGroupName].Last().Match(other) != null;
}
}
}

33
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Choice.cs

@ -0,0 +1,33 @@ @@ -0,0 +1,33 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
namespace ICSharpCode.NRefactory.CSharp.PatternMatching
{
/// <summary>
/// Matches one of several alternatives.
/// </summary>
public class Choice : Pattern
{
public static readonly Role<AstNode> AlternativeRole = new Role<AstNode>("Alternative", AstNode.Null);
public Choice(params AstNode[] alternatives)
{
foreach (AstNode node in alternatives)
AddChild(node, AlternativeRole);
}
protected internal override bool DoMatch(AstNode other, Match match)
{
var checkPoint = match.CheckPoint();
foreach (AstNode alt in GetChildrenByRole(AlternativeRole)) {
if (alt.DoMatch(other, match))
return true;
else
match.RestoreCheckPoint(checkPoint);
}
return false;
}
}
}

43
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Match.cs

@ -0,0 +1,43 @@ @@ -0,0 +1,43 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
using System.Collections.Generic;
using System.Linq;
namespace ICSharpCode.NRefactory.CSharp.PatternMatching
{
/// <summary>
/// Represents the result of a pattern matching operation.
/// </summary>
public sealed class Match
{
List<KeyValuePair<string, AstNode>> results = new List<KeyValuePair<string, AstNode>>();
internal int CheckPoint()
{
return results.Count;
}
internal void RestoreCheckPoint(int checkPoint)
{
results.RemoveRange(checkPoint, results.Count - checkPoint);
}
public IEnumerable<AstNode> this[string groupName] {
get {
foreach (var pair in results) {
if (pair.Key == groupName)
yield return pair.Value;
}
}
}
public void Add(string groupName, AstNode node)
{
if (groupName != null && node != null) {
results.Add(new KeyValuePair<string, AstNode>(groupName, node));
}
}
}
}

29
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/NamedGroup.cs

@ -0,0 +1,29 @@ @@ -0,0 +1,29 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
namespace ICSharpCode.NRefactory.CSharp.PatternMatching
{
/// <summary>
/// Represents a named node within a pattern.
/// </summary>
public class NamedNode : Pattern
{
public static readonly Role<AstNode> ElementRole = new Role<AstNode>("Element", AstNode.Null);
readonly string groupName;
public NamedNode(string groupName, AstNode childNode)
{
this.groupName = groupName;
AddChild(childNode, ElementRole);
}
protected internal override bool DoMatch(AstNode other, Match match)
{
match.Add(this.groupName, other);
return GetChildByRole(ElementRole).DoMatch(other, match);
}
}
}

42
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Pattern.cs

@ -0,0 +1,42 @@ @@ -0,0 +1,42 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
namespace ICSharpCode.NRefactory.CSharp.PatternMatching
{
/// <summary>
/// Base class for all patterns.
/// </summary>
public abstract class Pattern : AstNode
{
public override NodeType NodeType {
get { return NodeType.Pattern; }
}
public override S AcceptVisitor<T, S>(IAstVisitor<T, S> visitor, T data)
{
return default(S);
}
public AstType ToType()
{
return new TypePlaceholder(this);
}
public Expression ToExpression()
{
return new ExpressionPlaceholder(this);
}
public BlockStatement ToBlock()
{
return new BlockStatementPlaceholder(this);
}
public VariableInitializer ToVariable()
{
return new VariablePlaceholder(this);
}
}
}

119
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PatternMatching/Placeholder.cs

@ -0,0 +1,119 @@ @@ -0,0 +1,119 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
namespace ICSharpCode.NRefactory.CSharp.PatternMatching
{
sealed class TypePlaceholder : AstType
{
public static readonly Role<Pattern> PatternRole = new Role<Pattern>("Pattern");
public TypePlaceholder(Pattern pattern)
{
AddChild(pattern, TypePlaceholder.PatternRole);
}
public override NodeType NodeType {
get { return NodeType.Pattern; }
}
public override S AcceptVisitor<T, S>(IAstVisitor<T, S> visitor, T data)
{
return default(S);
}
protected internal override bool DoMatch(AstNode other, Match match)
{
return GetChildByRole(TypePlaceholder.PatternRole).DoMatch(other, match);
}
}
sealed class ExpressionPlaceholder : Expression
{
public ExpressionPlaceholder(Pattern pattern)
{
AddChild(pattern, TypePlaceholder.PatternRole);
}
public override NodeType NodeType {
get { return NodeType.Pattern; }
}
public override S AcceptVisitor<T, S>(IAstVisitor<T, S> visitor, T data)
{
return default(S);
}
protected internal override bool DoMatch(AstNode other, Match match)
{
return GetChildByRole(TypePlaceholder.PatternRole).DoMatch(other, match);
}
}
sealed class StatementPlaceholder : Statement
{
public StatementPlaceholder(Pattern pattern)
{
AddChild(pattern, TypePlaceholder.PatternRole);
}
public override NodeType NodeType {
get { return NodeType.Pattern; }
}
public override S AcceptVisitor<T, S>(IAstVisitor<T, S> visitor, T data)
{
return default(S);
}
protected internal override bool DoMatch(AstNode other, Match match)
{
return GetChildByRole(TypePlaceholder.PatternRole).DoMatch(other, match);
}
}
sealed class BlockStatementPlaceholder : BlockStatement
{
public BlockStatementPlaceholder(Pattern pattern)
{
AddChild(pattern, TypePlaceholder.PatternRole);
}
public override NodeType NodeType {
get { return NodeType.Pattern; }
}
public override S AcceptVisitor<T, S>(IAstVisitor<T, S> visitor, T data)
{
return default(S);
}
protected internal override bool DoMatch(AstNode other, Match match)
{
return GetChildByRole(TypePlaceholder.PatternRole).DoMatch(other, match);
}
}
sealed class VariablePlaceholder : VariableInitializer
{
public VariablePlaceholder(Pattern pattern)
{
AddChild(pattern, TypePlaceholder.PatternRole);
}
public override NodeType NodeType {
get { return NodeType.Pattern; }
}
public override S AcceptVisitor<T, S>(IAstVisitor<T, S> visitor, T data)
{
return default(S);
}
protected internal override bool DoMatch(AstNode other, Match match)
{
return GetChildByRole(TypePlaceholder.PatternRole).DoMatch(other, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/PrimitiveType.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// FullTypeName.cs
//
// Author:
@ -65,6 +65,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -65,6 +65,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitPrimitiveType (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
PrimitiveType o = other as PrimitiveType;
return o != null && MatchString(this.Keyword, o.Keyword);
}
public override string ToString()
{
return Keyword ?? base.ToString();

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/SimpleType.cs

@ -65,6 +65,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -65,6 +65,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitSimpleType (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
SimpleType o = other as SimpleType;
return o != null && MatchString(this.Identifier, o.Identifier) && this.TypeArguments.DoMatch(o.TypeArguments, match);
}
public override string ToString()
{
StringBuilder b = new StringBuilder(this.Identifier);

11
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/BlockStatement.cs

@ -49,6 +49,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -49,6 +49,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return default (S);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
return other == null || other.IsNull;
}
}
#endregion
@ -69,6 +74,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -69,6 +74,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitBlockStatement (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
BlockStatement o = other as BlockStatement;
return o != null && this.Statements.DoMatch(o.Statements, match);
}
#region Builder methods
public void AddStatement(Statement statement)
{

10
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/BreakStatement.cs

@ -1,6 +1,6 @@ @@ -1,6 +1,6 @@
//
//
// BreakStatement.cs
//
//
// Author:
// Mike Krüger <mkrueger@novell.com>
//
@ -39,5 +39,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -39,5 +39,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitBreakStatement (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
BreakStatement o = other as BreakStatement;
return o != null;
}
}
}

17
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/ExpressionStatement.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// ExpressionStatement.cs
//
// Author:
@ -44,5 +44,20 @@ namespace ICSharpCode.NRefactory.CSharp @@ -44,5 +44,20 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitExpressionStatement (this, data);
}
public ExpressionStatement()
{
}
public ExpressionStatement(Expression expression)
{
this.Expression = expression;
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ExpressionStatement o = other as ExpressionStatement;
return o != null && this.Expression.DoMatch(o.Expression, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/IfElseStatement.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// IfElseStatement.cs
//
// Author:
@ -74,6 +74,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -74,6 +74,12 @@ namespace ICSharpCode.NRefactory.CSharp
return visitor.VisitIfElseStatement (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
IfElseStatement o = other as IfElseStatement;
return o != null && this.Condition.DoMatch(o.Condition, match) && this.TrueStatement.DoMatch(o.TrueStatement, match) && this.FalseStatement.DoMatch(o.FalseStatement, match);
}
public IfElseStatement()
{
}

10
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/Statement.cs

@ -29,6 +29,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -29,6 +29,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return default (S);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
return other == null || other.IsNull;
}
}
#endregion
@ -47,5 +52,10 @@ namespace ICSharpCode.NRefactory.CSharp @@ -47,5 +52,10 @@ namespace ICSharpCode.NRefactory.CSharp
public override NodeType NodeType {
get { return NodeType.Statement; }
}
protected internal override bool DoMatch(AstNode other, ICSharpCode.NRefactory.CSharp.PatternMatching.Match match)
{
throw new NotImplementedException();
}
}
}

12
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/SwitchStatement.cs

@ -93,6 +93,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -93,6 +93,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitSwitchSection (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
SwitchSection o = other as SwitchSection;
return o != null && this.CaseLabels.DoMatch(o.CaseLabels, match) && this.Statements.DoMatch(o.Statements, match);
}
}
public class CaseLabel : AstNode
@ -112,5 +118,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -112,5 +118,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitCaseLabel (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
CaseLabel o = other as CaseLabel;
return o != null && this.Expression.DoMatch(o.Expression, match);
}
}
}

12
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/TryCatchStatement.cs

@ -66,6 +66,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -66,6 +66,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitTryCatchStatement (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
TryCatchStatement o = other as TryCatchStatement;
return o != null && this.TryBlock.DoMatch(o.TryBlock, match) && this.CatchClauses.DoMatch(o.CatchClauses, match) && this.FinallyBlock.DoMatch(o.FinallyBlock, match);
}
}
/// <summary>
@ -115,5 +121,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -115,5 +121,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitCatchClause (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
CatchClause o = other as CatchClause;
return o != null && this.Type.DoMatch(o.Type, match) && MatchString(this.VariableName, o.VariableName) && this.Body.DoMatch(o.Body, match);
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/Statements/VariableDeclarationStatement.cs

@ -65,5 +65,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -65,5 +65,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitVariableDeclarationStatement (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
VariableDeclarationStatement o = other as VariableDeclarationStatement;
return o != null && this.Modifiers == o.Modifiers && this.Type.DoMatch(o.Type, match) && this.Variables.DoMatch(o.Variables, match);
}
}
}

9
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/Accessor.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// PropertyDeclaration.cs
//
// Author:
@ -24,6 +24,8 @@ @@ -24,6 +24,8 @@
// OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
// THE SOFTWARE.
using System;
namespace ICSharpCode.NRefactory.CSharp
{
/// <summary>
@ -59,5 +61,10 @@ namespace ICSharpCode.NRefactory.CSharp @@ -59,5 +61,10 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitAccessor (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
throw new NotImplementedException();
}
}
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/AttributedNode.cs

@ -1,6 +1,7 @@ @@ -1,6 +1,7 @@
// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
// This code is distributed under MIT X11 license (for details please see \doc\license.txt)
using System;
using System.Collections.Generic;
using System.Linq;
@ -56,5 +57,10 @@ namespace ICSharpCode.NRefactory.CSharp @@ -56,5 +57,10 @@ namespace ICSharpCode.NRefactory.CSharp
}
}
}
protected internal override bool DoMatch(AstNode other, ICSharpCode.NRefactory.CSharp.PatternMatching.Match match)
{
throw new NotImplementedException();
}
}
}

13
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/ConstructorDeclaration.cs

@ -33,6 +33,13 @@ namespace ICSharpCode.NRefactory.CSharp @@ -33,6 +33,13 @@ namespace ICSharpCode.NRefactory.CSharp
{
public static readonly Role<ConstructorInitializer> InitializerRole = new Role<ConstructorInitializer>("Initializer", ConstructorInitializer.Null);
/// <summary>
/// Gets/Sets the name of the class containing the constructor.
/// This property can be used to inform the output visitor about the class name when writing a constructor declaration
/// without writing the complete type declaration. It is ignored when the constructor has a type declaration as parent.
/// </summary>
public string Name { get; set; }
public CSharpTokenNode LParToken {
get { return GetChildByRole (Roles.LPar); }
}
@ -112,5 +119,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -112,5 +119,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitConstructorInitializer (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ConstructorInitializer o = other as ConstructorInitializer;
return o != null && this.ConstructorInitializerType == o.ConstructorInitializerType && this.Arguments.DoMatch(o.Arguments, match);
}
}
}

9
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/DestructorDeclaration.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// DestructorDeclaration.cs
//
// Author:
@ -34,6 +34,13 @@ namespace ICSharpCode.NRefactory.CSharp @@ -34,6 +34,13 @@ namespace ICSharpCode.NRefactory.CSharp
get { return GetChildByRole (TildeRole); }
}
/// <summary>
/// Gets/Sets the name of the class containing the destructor.
/// This property can be used to inform the output visitor about the class name when writing a destructor declaration
/// without writing the complete type declaration. It is ignored when the destructor has a type declaration as parent.
/// </summary>
public string Name { get; set; }
public CSharpTokenNode LParToken {
get { return GetChildByRole (Roles.LPar); }
}

6
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/ParameterDeclaration.cs

@ -81,6 +81,12 @@ namespace ICSharpCode.NRefactory.CSharp @@ -81,6 +81,12 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitParameterDeclaration (this, data);
}
protected internal override bool DoMatch(AstNode other, PatternMatching.Match match)
{
ParameterDeclaration o = other as ParameterDeclaration;
return o != null && this.Attributes.DoMatch(o.Attributes, match) && this.ParameterModifier == o.ParameterModifier && MatchString(this.Name, o.Name) && this.DefaultExpression.DoMatch(o.DefaultExpression, match);
}
}
}

8
NRefactory/ICSharpCode.NRefactory/CSharp/Ast/TypeMembers/VariableInitializer.cs

@ -1,4 +1,4 @@ @@ -1,4 +1,4 @@
//
//
// VariableInitializer.cs
//
// Author:
@ -66,5 +66,11 @@ namespace ICSharpCode.NRefactory.CSharp @@ -66,5 +66,11 @@ namespace ICSharpCode.NRefactory.CSharp
{
return visitor.VisitVariableInitializer (this, data);
}
protected internal override bool DoMatch(AstNode other, ICSharpCode.NRefactory.CSharp.PatternMatching.Match match)
{
VariableInitializer o = other as VariableInitializer;
return o != null && MatchString(this.Name, o.Name) && this.Initializer.DoMatch(o.Initializer, match);
}
}
}

10
NRefactory/ICSharpCode.NRefactory/CSharp/OutputVisitor/OutputVisitor.cs

@ -263,7 +263,7 @@ namespace ICSharpCode.NRefactory.CSharp @@ -263,7 +263,7 @@ namespace ICSharpCode.NRefactory.CSharp
/// </summary>
void Semicolon()
{
if (!(currentContainerNode.Parent is ForStatement)) {
if (currentContainerNode.Role != ForStatement.InitializerRole && currentContainerNode.Role != ForStatement.IteratorRole && currentContainerNode.Role != UsingStatement.ResourceAcquisitionRole) {
WriteToken(";", AstNode.Roles.Semicolon);
NewLine();
}
@ -1626,9 +1626,7 @@ namespace ICSharpCode.NRefactory.CSharp @@ -1626,9 +1626,7 @@ namespace ICSharpCode.NRefactory.CSharp
WriteAttributes(constructorDeclaration.Attributes);
WriteModifiers(constructorDeclaration.ModifierTokens);
TypeDeclaration type = constructorDeclaration.Parent as TypeDeclaration;
if (type != null) {
WriteIdentifier(type.Name);
}
WriteIdentifier(type != null ? type.Name : constructorDeclaration.Name);
Space(policy.BeforeConstructorDeclarationParentheses);
WriteCommaSeparatedListInParenthesis(constructorDeclaration.Parameters, policy.WithinMethodDeclarationParentheses);
if (!constructorDeclaration.Initializer.IsNull) {
@ -1661,9 +1659,7 @@ namespace ICSharpCode.NRefactory.CSharp @@ -1661,9 +1659,7 @@ namespace ICSharpCode.NRefactory.CSharp
WriteModifiers(destructorDeclaration.ModifierTokens);
WriteToken("~", DestructorDeclaration.TildeRole);
TypeDeclaration type = destructorDeclaration.Parent as TypeDeclaration;
if (type != null) {
WriteIdentifier(type.Name);
}
WriteIdentifier(type != null ? type.Name : destructorDeclaration.Name);
Space(policy.BeforeConstructorDeclarationParentheses);
LPar();
RPar();

9
NRefactory/ICSharpCode.NRefactory/ICSharpCode.NRefactory.csproj

@ -55,7 +55,6 @@ @@ -55,7 +55,6 @@
</Reference>
</ItemGroup>
<ItemGroup>
<Compile Include="CSharp\Ast\AstComparer.cs" />
<Compile Include="CSharp\Ast\AstNodeCollection.cs" />
<Compile Include="CSharp\Ast\Expressions\TypeReferenceExpression.cs" />
<Compile Include="CSharp\Ast\IAstVisitor.cs" />
@ -96,6 +95,13 @@ @@ -96,6 +95,13 @@
<Compile Include="CSharp\Ast\Expressions\UncheckedExpression.cs" />
<Compile Include="CSharp\Ast\GeneralScope\TypeParameterDeclaration.cs" />
<Compile Include="CSharp\Ast\MemberType.cs" />
<Compile Include="CSharp\Ast\PatternMatching\Choice.cs" />
<Compile Include="CSharp\Ast\PatternMatching\AnyNode.cs" />
<Compile Include="CSharp\Ast\PatternMatching\Backreference.cs" />
<Compile Include="CSharp\Ast\PatternMatching\Match.cs" />
<Compile Include="CSharp\Ast\PatternMatching\NamedGroup.cs" />
<Compile Include="CSharp\Ast\PatternMatching\Pattern.cs" />
<Compile Include="CSharp\Ast\PatternMatching\Placeholder.cs" />
<Compile Include="CSharp\Ast\NotImplementedAstVisitor.cs" />
<Compile Include="CSharp\Ast\PrimitiveType.cs" />
<Compile Include="CSharp\Ast\GeneralScope\Attribute.cs" />
@ -336,6 +342,7 @@ @@ -336,6 +342,7 @@
</ItemGroup>
<ItemGroup>
<Folder Include="CSharp\" />
<Folder Include="CSharp\Ast\PatternMatching" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\..\Mono.Cecil\Mono.Cecil.csproj">

Loading…
Cancel
Save