Browse Source

Add back AST transform infrastructure

pull/728/head
Daniel Grunwald 11 years ago
parent
commit
e0a1666547
  1. 50
      ICSharpCode.Decompiler/Ast/Annotations.cs
  2. 14
      ICSharpCode.Decompiler/CSharp/Annotations.cs
  3. 18
      ICSharpCode.Decompiler/CSharp/CSharpDecompiler.cs
  4. 3
      ICSharpCode.Decompiler/CSharp/Transforms/AddCheckedBlocks.cs
  5. 0
      ICSharpCode.Decompiler/CSharp/Transforms/CombineQueryExpressions.cs
  6. 0
      ICSharpCode.Decompiler/CSharp/Transforms/ContextTrackingVisitor.cs
  7. 0
      ICSharpCode.Decompiler/CSharp/Transforms/ConvertConstructorCallIntoInitializer.cs
  8. 2
      ICSharpCode.Decompiler/CSharp/Transforms/CustomPatterns.cs
  9. 0
      ICSharpCode.Decompiler/CSharp/Transforms/DecimalConstantTransform.cs
  10. 0
      ICSharpCode.Decompiler/CSharp/Transforms/DeclareVariables.cs
  11. 0
      ICSharpCode.Decompiler/CSharp/Transforms/DelegateConstruction.cs
  12. 0
      ICSharpCode.Decompiler/CSharp/Transforms/ExpressionTreeConverter.cs
  13. 0
      ICSharpCode.Decompiler/CSharp/Transforms/FlattenSwitchBlocks.cs
  14. 39
      ICSharpCode.Decompiler/CSharp/Transforms/IAstTransform.cs
  15. 0
      ICSharpCode.Decompiler/CSharp/Transforms/IntroduceExtensionMethods.cs
  16. 0
      ICSharpCode.Decompiler/CSharp/Transforms/IntroduceQueryExpressions.cs
  17. 0
      ICSharpCode.Decompiler/CSharp/Transforms/IntroduceUnsafeModifier.cs
  18. 0
      ICSharpCode.Decompiler/CSharp/Transforms/IntroduceUsingDeclarations.cs
  19. 0
      ICSharpCode.Decompiler/CSharp/Transforms/PatternStatementTransform.cs
  20. 0
      ICSharpCode.Decompiler/CSharp/Transforms/PushNegation.cs
  21. 21
      ICSharpCode.Decompiler/CSharp/Transforms/ReplaceMethodCallsWithOperators.cs
  22. 0
      ICSharpCode.Decompiler/CSharp/Transforms/TransformationPipeline.cs
  23. 8
      ICSharpCode.Decompiler/ICSharpCode.Decompiler.csproj

50
ICSharpCode.Decompiler/Ast/Annotations.cs

@ -1,50 +0,0 @@ @@ -1,50 +0,0 @@
using System;
using System.Collections.Generic;
using System.Diagnostics;
using ICSharpCode.Decompiler.ILAst;
using ICSharpCode.NRefactory.CSharp;
using Mono.Cecil;
namespace ICSharpCode.Decompiler.Ast
{
public class TypeInformation
{
public readonly TypeReference InferredType;
public TypeInformation(TypeReference inferredType)
{
this.InferredType = inferredType;
}
}
public class LdTokenAnnotation {}
/// <summary>
/// Annotation that is applied to the body expression of an Expression.Lambda() call.
/// </summary>
public class ParameterDeclarationAnnotation
{
public readonly List<ParameterDeclaration> Parameters = new List<ParameterDeclaration>();
public ParameterDeclarationAnnotation(ILExpression expr)
{
Debug.Assert(expr.Code == ILCode.ExpressionTreeParameterDeclarations);
for (int i = 0; i < expr.Arguments.Count - 1; i++) {
ILExpression p = expr.Arguments[i];
// p looks like this:
// stloc(v, call(Expression::Parameter, call(Type::GetTypeFromHandle, ldtoken(...)), ldstr(...)))
ILVariable v = (ILVariable)p.Operand;
TypeReference typeRef = (TypeReference)p.Arguments[0].Arguments[0].Arguments[0].Operand;
string name = (string)p.Arguments[0].Arguments[1].Operand;
Parameters.Add(new ParameterDeclaration(AstBuilder.ConvertType(typeRef), name).WithAnnotation(v));
}
}
}
/// <summary>
/// Annotation that is applied to a LambdaExpression that was produced by an expression tree.
/// </summary>
public class ExpressionTreeLambdaAnnotation
{
}
}

14
ICSharpCode.Decompiler/CSharp/Annotations.cs

@ -0,0 +1,14 @@ @@ -0,0 +1,14 @@
/*
* Created by SharpDevelop.
* User: Daniel
* Date: 2014-08-24
* Time: 18:42
*
* To change this template use Tools | Options | Coding | Edit Standard Headers.
*/
using System;
namespace ICSharpCode.Decompiler.CSharp
{
public class LdTokenAnnotation {}
}

18
ICSharpCode.Decompiler/CSharp/CSharpDecompiler.cs

@ -16,6 +16,7 @@ @@ -16,6 +16,7 @@
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
// DEALINGS IN THE SOFTWARE.
using ICSharpCode.Decompiler.CSharp.Transforms;
using ICSharpCode.Decompiler.IL;
using ICSharpCode.NRefactory.CSharp;
using ICSharpCode.NRefactory.CSharp.Refactoring;
@ -39,9 +40,17 @@ namespace ICSharpCode.Decompiler.CSharp @@ -39,9 +40,17 @@ namespace ICSharpCode.Decompiler.CSharp
NRefactoryCecilMapper cecilMapper;
ICompilation compilation;
TypeSystemAstBuilder typeSystemAstBuilder;
List<IAstTransform> astTransforms = new List<IAstTransform>(TransformationPipeline.CreatePipeline());
public CancellationToken CancellationToken { get; set; }
/// <summary>
/// C# AST transforms.
/// </summary>
public IList<IAstTransform> AstTransforms {
get { return astTransforms; }
}
public CSharpDecompiler(ModuleDefinition module)
{
cecilLoader.OnEntityLoaded = (entity, mr) => {
@ -143,9 +152,9 @@ namespace ICSharpCode.Decompiler.CSharp @@ -143,9 +152,9 @@ namespace ICSharpCode.Decompiler.CSharp
function.CheckInvariant();
var statementBuilder = new StatementBuilder(method, cecilMapper);
var body = statementBuilder.ConvertAsBlock(function.Body);
body.AcceptVisitor(new InsertParenthesesVisitor {
InsertParenthesesForReadability = true
});
foreach (var transform in astTransforms) {
transform.Run(body);
}
// insert variables at start of body
Statement prevVarDecl = null;
foreach (var v in function.Variables) {
@ -156,6 +165,9 @@ namespace ICSharpCode.Decompiler.CSharp @@ -156,6 +165,9 @@ namespace ICSharpCode.Decompiler.CSharp
prevVarDecl = varDecl;
}
}
body.AcceptVisitor(new InsertParenthesesVisitor {
InsertParenthesesForReadability = true
});
entityDecl.AddChild(body, Roles.Body);
}
return entityDecl;

3
ICSharpCode.Decompiler/Ast/Transforms/AddCheckedBlocks.cs → ICSharpCode.Decompiler/CSharp/Transforms/AddCheckedBlocks.cs

@ -18,10 +18,9 @@ @@ -18,10 +18,9 @@
using System;
using System.Linq;
using ICSharpCode.Decompiler.ILAst;
using ICSharpCode.NRefactory.CSharp;
namespace ICSharpCode.Decompiler.Ast.Transforms
namespace ICSharpCode.Decompiler.CSharp.Transforms
{
/// <summary>
/// Add checked/unchecked blocks.

0
ICSharpCode.Decompiler/Ast/Transforms/CombineQueryExpressions.cs → ICSharpCode.Decompiler/CSharp/Transforms/CombineQueryExpressions.cs

0
ICSharpCode.Decompiler/Ast/Transforms/ContextTrackingVisitor.cs → ICSharpCode.Decompiler/CSharp/Transforms/ContextTrackingVisitor.cs

0
ICSharpCode.Decompiler/Ast/Transforms/ConvertConstructorCallIntoInitializer.cs → ICSharpCode.Decompiler/CSharp/Transforms/ConvertConstructorCallIntoInitializer.cs

2
ICSharpCode.Decompiler/Ast/Transforms/CustomPatterns.cs → ICSharpCode.Decompiler/CSharp/Transforms/CustomPatterns.cs

@ -23,7 +23,7 @@ using ICSharpCode.NRefactory.CSharp; @@ -23,7 +23,7 @@ using ICSharpCode.NRefactory.CSharp;
using ICSharpCode.NRefactory.PatternMatching;
using Mono.Cecil;
namespace ICSharpCode.Decompiler.Ast.Transforms
namespace ICSharpCode.Decompiler.CSharp.Transforms
{
sealed class TypePattern : Pattern
{

0
ICSharpCode.Decompiler/Ast/Transforms/DecimalConstantTransform.cs → ICSharpCode.Decompiler/CSharp/Transforms/DecimalConstantTransform.cs

0
ICSharpCode.Decompiler/Ast/Transforms/DeclareVariables.cs → ICSharpCode.Decompiler/CSharp/Transforms/DeclareVariables.cs

0
ICSharpCode.Decompiler/Ast/Transforms/DelegateConstruction.cs → ICSharpCode.Decompiler/CSharp/Transforms/DelegateConstruction.cs

0
ICSharpCode.Decompiler/Ast/Transforms/ExpressionTreeConverter.cs → ICSharpCode.Decompiler/CSharp/Transforms/ExpressionTreeConverter.cs

0
ICSharpCode.Decompiler/Ast/Transforms/FlattenSwitchBlocks.cs → ICSharpCode.Decompiler/CSharp/Transforms/FlattenSwitchBlocks.cs

39
ICSharpCode.Decompiler/CSharp/Transforms/IAstTransform.cs

@ -0,0 +1,39 @@ @@ -0,0 +1,39 @@
// Copyright (c) 2011 AlphaSierraPapa for the SharpDevelop Team
//
// Permission is hereby granted, free of charge, to any person obtaining a copy of this
// software and associated documentation files (the "Software"), to deal in the Software
// without restriction, including without limitation the rights to use, copy, modify, merge,
// publish, distribute, sublicense, and/or sell copies of the Software, and to permit persons
// to whom the Software is furnished to do so, subject to the following conditions:
//
// The above copyright notice and this permission notice shall be included in all copies or
// substantial portions of the Software.
//
// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED,
// INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
// PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE
// FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
// OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
// DEALINGS IN THE SOFTWARE.
using System;
using System.Threading;
using ICSharpCode.NRefactory.CSharp;
namespace ICSharpCode.Decompiler.CSharp.Transforms
{
public interface IAstTransform
{
void Run(AstNode compilationUnit);
}
public static class TransformationPipeline
{
public static IAstTransform[] CreatePipeline()
{
return new IAstTransform[] {
new AddCheckedBlocks()
};
}
}
}

0
ICSharpCode.Decompiler/Ast/Transforms/IntroduceExtensionMethods.cs → ICSharpCode.Decompiler/CSharp/Transforms/IntroduceExtensionMethods.cs

0
ICSharpCode.Decompiler/Ast/Transforms/IntroduceQueryExpressions.cs → ICSharpCode.Decompiler/CSharp/Transforms/IntroduceQueryExpressions.cs

0
ICSharpCode.Decompiler/Ast/Transforms/IntroduceUnsafeModifier.cs → ICSharpCode.Decompiler/CSharp/Transforms/IntroduceUnsafeModifier.cs

0
ICSharpCode.Decompiler/Ast/Transforms/IntroduceUsingDeclarations.cs → ICSharpCode.Decompiler/CSharp/Transforms/IntroduceUsingDeclarations.cs

0
ICSharpCode.Decompiler/Ast/Transforms/PatternStatementTransform.cs → ICSharpCode.Decompiler/CSharp/Transforms/PatternStatementTransform.cs

0
ICSharpCode.Decompiler/Ast/Transforms/PushNegation.cs → ICSharpCode.Decompiler/CSharp/Transforms/PushNegation.cs

21
ICSharpCode.Decompiler/Ast/Transforms/ReplaceMethodCallsWithOperators.cs → ICSharpCode.Decompiler/CSharp/Transforms/ReplaceMethodCallsWithOperators.cs

@ -25,7 +25,7 @@ using Mono.Cecil; @@ -25,7 +25,7 @@ using Mono.Cecil;
using Ast = ICSharpCode.NRefactory.CSharp;
using ICSharpCode.NRefactory.CSharp;
namespace ICSharpCode.Decompiler.Ast.Transforms
namespace ICSharpCode.Decompiler.CSharp.Transforms
{
/// <summary>
/// Replaces method calls with the appropriate operator expressions.
@ -41,13 +41,6 @@ namespace ICSharpCode.Decompiler.Ast.Transforms @@ -41,13 +41,6 @@ namespace ICSharpCode.Decompiler.Ast.Transforms
MemberName = "TypeHandle"
};
DecompilerContext context;
public ReplaceMethodCallsWithOperators(DecompilerContext context)
{
this.context = context;
}
public override object VisitInvocationExpression(InvocationExpression invocationExpression, object data)
{
base.VisitInvocationExpression(invocationExpression, data);
@ -131,7 +124,7 @@ namespace ICSharpCode.Decompiler.Ast.Transforms @@ -131,7 +124,7 @@ namespace ICSharpCode.Decompiler.Ast.Transforms
if (methodRef.Name == "op_Explicit" && arguments.Length == 1) {
arguments[0].Remove(); // detach argument
invocationExpression.ReplaceWith(
arguments[0].CastTo(AstBuilder.ConvertType(methodRef.ReturnType, methodRef.MethodReturnType))
arguments[0].CastTo(ConvertType(methodRef.ReturnType, methodRef.MethodReturnType))
.WithAnnotation(methodRef)
);
return;
@ -254,7 +247,8 @@ namespace ICSharpCode.Decompiler.Ast.Transforms @@ -254,7 +247,8 @@ namespace ICSharpCode.Decompiler.Ast.Transforms
}
}
}
if (context.Settings.IntroduceIncrementAndDecrement && (assignment.Operator == AssignmentOperatorType.Add || assignment.Operator == AssignmentOperatorType.Subtract)) {
// TODO: context.Settings.IntroduceIncrementAndDecrement
if (assignment.Operator == AssignmentOperatorType.Add || assignment.Operator == AssignmentOperatorType.Subtract) {
// detect increment/decrement
if (assignment.Right.IsMatch(new PrimitiveExpression(1))) {
// only if it's not a custom operator
@ -329,6 +323,11 @@ namespace ICSharpCode.Decompiler.Ast.Transforms @@ -329,6 +323,11 @@ namespace ICSharpCode.Decompiler.Ast.Transforms
new TypePattern(typeof(MethodInfo)),
new TypePattern(typeof(ConstructorInfo))
});
static AstType ConvertType(TypeReference parameterType, object ctx)
{
return new SimpleType(parameterType.Name);
}
public override object VisitCastExpression(CastExpression castExpression, object data)
{
@ -339,7 +338,7 @@ namespace ICSharpCode.Decompiler.Ast.Transforms @@ -339,7 +338,7 @@ namespace ICSharpCode.Decompiler.Ast.Transforms
MethodReference method = m.Get<AstNode>("method").Single().Annotation<MethodReference>();
if (m.Has("declaringType")) {
Expression newNode = m.Get<AstType>("declaringType").Single().Detach().Member(method.Name);
newNode = newNode.Invoke(method.Parameters.Select(p => new TypeReferenceExpression(AstBuilder.ConvertType(p.ParameterType, p))));
newNode = newNode.Invoke(method.Parameters.Select(p => new TypeReferenceExpression(ConvertType(p.ParameterType, p))));
newNode.AddAnnotation(method);
m.Get<AstNode>("method").Single().ReplaceWith(newNode);
}

0
ICSharpCode.Decompiler/Ast/Transforms/TransformationPipeline.cs → ICSharpCode.Decompiler/CSharp/Transforms/TransformationPipeline.cs

8
ICSharpCode.Decompiler/ICSharpCode.Decompiler.csproj

@ -62,12 +62,17 @@ @@ -62,12 +62,17 @@
</Reference>
</ItemGroup>
<ItemGroup>
<Compile Include="CSharp\Annotations.cs" />
<Compile Include="CSharp\ConvertedExpression.cs" />
<Compile Include="CSharp\NRefactoryCecilMapper.cs" />
<Compile Include="CSharp\CSharpDecompiler.cs" />
<Compile Include="CSharp\ExpressionBuilder.cs" />
<Compile Include="CSharp\NRefactoryExtensions.cs" />
<Compile Include="CSharp\StatementBuilder.cs" />
<Compile Include="CSharp\Transforms\AddCheckedBlocks.cs" />
<Compile Include="CSharp\Transforms\CustomPatterns.cs" />
<Compile Include="CSharp\Transforms\IAstTransform.cs" />
<Compile Include="CSharp\Transforms\ReplaceMethodCallsWithOperators.cs" />
<Compile Include="IL\Instructions.cs">
<AutoGen>True</AutoGen>
<DesignTime>True</DesignTime>
@ -153,6 +158,9 @@ @@ -153,6 +158,9 @@
<ItemGroup>
<Service Include="{508349B6-6B84-4DF5-91F0-309BEEBAD82D}" />
</ItemGroup>
<ItemGroup>
<Folder Include="CSharp\Transforms" />
</ItemGroup>
<Import Project="$(MSBuildBinPath)\Microsoft.CSharp.Targets" />
<Target Name="BeforeBuild">
<MSBuild Projects="$(MSBuildProjectDirectory)\..\BuildTools\UpdateAssemblyInfo\UpdateAssemblyInfo.csproj" Targets="Build" Properties="Configuration=Debug" />

Loading…
Cancel
Save