From c940b7b7678923bc7196c4775ecfcc41c8cc233b Mon Sep 17 00:00:00 2001 From: Siegfried Pammer Date: Sun, 26 Jun 2016 19:29:31 +0900 Subject: [PATCH] add missing casts to property- and event-uses --- .../CSharp/ExpressionBuilder.cs | 30 ++++++++++++------- .../Tests/TestCases/MemberLookup.cs | 25 ++++++++++++++++ 2 files changed, 44 insertions(+), 11 deletions(-) diff --git a/ICSharpCode.Decompiler/CSharp/ExpressionBuilder.cs b/ICSharpCode.Decompiler/CSharp/ExpressionBuilder.cs index 2d124a56e..47f85be38 100644 --- a/ICSharpCode.Decompiler/CSharp/ExpressionBuilder.cs +++ b/ICSharpCode.Decompiler/CSharp/ExpressionBuilder.cs @@ -719,14 +719,15 @@ namespace ICSharpCode.Decompiler.CSharp else rr = new CSharpInvocationResolveResult(target.ResolveResult, method, argumentResolveResults); - var argumentExpressions = arguments.Skip(firstParamIndex).Select(arg => arg.Expression).ToList(); if (inst.OpCode == OpCode.NewObj) { + var argumentExpressions = arguments.Skip(firstParamIndex).Select(arg => arg.Expression).ToList(); return new ObjectCreateExpression(ConvertType(inst.Method.DeclaringType), argumentExpressions) .WithILInstruction(inst).WithRR(rr); } else { Expression expr; - if (method.IsAccessor) { - expr = HandleAccessorCall(target, method, argumentExpressions); + int allowedParamCount = (method.ReturnType.IsKnownType(KnownTypeCode.Void) ? 1 : 0); + if (method.IsAccessor && (method.AccessorOwner.SymbolKind == SymbolKind.Indexer || method.Parameters.Count == allowedParamCount)) { + expr = HandleAccessorCall(inst, target, method, arguments.Skip(firstParamIndex).ToList()); } else { var lookup = new MemberLookup(resolver.CurrentTypeDefinition, resolver.CurrentTypeDefinition.ParentAssembly); var or = new OverloadResolution(resolver.Compilation, arguments.Skip(firstParamIndex).Select(a => a.ResolveResult).ToArray()); @@ -749,22 +750,29 @@ namespace ICSharpCode.Decompiler.CSharp } var mre = new MemberReferenceExpression(targetExpr, methodName); mre.TypeArguments.AddRange(method.TypeArguments.Select(a => ConvertType(a))); + var argumentExpressions = arguments.Skip(firstParamIndex).Select(arg => arg.Expression).ToList(); expr = new InvocationExpression(mre, argumentExpressions); } return expr.WithILInstruction(inst).WithRR(rr); } } - Expression HandleAccessorCall(TranslatedExpression target, IMethod method, IList argumentExpressions) + Expression HandleAccessorCall(ILInstruction inst, TranslatedExpression target, IMethod method, IList arguments) { + var lookup = new MemberLookup(resolver.CurrentTypeDefinition, resolver.CurrentTypeDefinition.ParentAssembly); + var result = lookup.Lookup(target.ResolveResult, method.AccessorOwner.Name, EmptyList.Instance, isInvocation:false); + + if (result.IsError || (result is MemberResolveResult && !IsAppropriateCallTarget(method.AccessorOwner, ((MemberResolveResult)result).Member, inst.OpCode == OpCode.CallVirt))) + target = target.ConvertTo(method.AccessorOwner.DeclaringType, this); + if (method.ReturnType.IsKnownType(KnownTypeCode.Void)) { - var value = argumentExpressions.Last(); - argumentExpressions.Remove(value); + var value = arguments.Last(); + arguments.Remove(value); Expression expr; - if (argumentExpressions.Count == 0) + if (arguments.Count == 0) expr = new MemberReferenceExpression(target.Expression, method.AccessorOwner.Name); else - expr = new IndexerExpression(target.Expression, argumentExpressions); + expr = new IndexerExpression(target.Expression, arguments.Select(a => a.Expression)); var op = AssignmentOperatorType.Assign; var parentEvent = method.AccessorOwner as IEvent; if (parentEvent != null) { @@ -775,12 +783,12 @@ namespace ICSharpCode.Decompiler.CSharp op = AssignmentOperatorType.Subtract; } } - return new AssignmentExpression(expr, op, value); + return new AssignmentExpression(expr, op, value.Expression); } else { - if (argumentExpressions.Count == 0) + if (arguments.Count == 0) return new MemberReferenceExpression(target.Expression, method.AccessorOwner.Name); else - return new IndexerExpression(target.Expression, argumentExpressions); + return new IndexerExpression(target.Expression, arguments.Select(a => a.Expression)); } } diff --git a/ICSharpCode.Decompiler/Tests/TestCases/MemberLookup.cs b/ICSharpCode.Decompiler/Tests/TestCases/MemberLookup.cs index 8e3504bfd..4fd25b93a 100644 --- a/ICSharpCode.Decompiler/Tests/TestCases/MemberLookup.cs +++ b/ICSharpCode.Decompiler/Tests/TestCases/MemberLookup.cs @@ -38,13 +38,23 @@ namespace ICSharpCode.Decompiler.Tests.TestCases protected virtual void TestMethod() { + Property = 5; Console.WriteLine("Base1.TestMethod()"); + Console.WriteLine(Property); } public void TestAction() { Console.WriteLine("Base1.TestAction()"); } + + public int Property { get; set; } + + public virtual int VirtProp { + get { + return 3; + } + } } class Child1 : Base1 @@ -57,20 +67,35 @@ namespace ICSharpCode.Decompiler.Tests.TestCases var o = new Child1(); o.child = new Child1(); o.TestMethod(); + + Console.WriteLine(((Base1)o).Property); + Console.WriteLine(o.Property); + Console.WriteLine(((Base1)o).VirtProp); + Console.WriteLine(o.VirtProp); } protected override void TestMethod() { + Property = 10; base.TestMethod(); if (child != null) child.TestMethod(); Console.WriteLine("Child1.TestMethod()"); + Console.WriteLine("Property = " + Property + " " + base.Property); } new public void TestAction() { Console.WriteLine("Child1.TestAction()"); } + + new public int Property { get; set; } + + public override int VirtProp { + get { + return base.VirtProp * 2; + } + } } } }