Browse Source

Fix #2307: potential NRE in IntroduceExtensionMethods

pull/2309/head
Siegfried Pammer 4 years ago
parent
commit
3431881345
  1. 13
      ICSharpCode.Decompiler/CSharp/ExpressionBuilder.cs
  2. 5
      ICSharpCode.Decompiler/CSharp/Transforms/IntroduceExtensionMethods.cs
  3. 5
      ICSharpCode.Decompiler/Semantics/ByReferenceResolveResult.cs

13
ICSharpCode.Decompiler/CSharp/ExpressionBuilder.cs

@ -217,10 +217,11 @@ namespace ICSharpCode.Decompiler.CSharp
// Ensure that the IdentifierExpression itself also gets a resolve result, as that might // Ensure that the IdentifierExpression itself also gets a resolve result, as that might
// get used after the 'ref' is stripped away: // get used after the 'ref' is stripped away:
var elementType = ((ByReferenceType)variable.Type).ElementType; var elementType = ((ByReferenceType)variable.Type).ElementType;
expr.WithRR(new ILVariableResolveResult(variable, elementType)); var elementRR = new ILVariableResolveResult(variable, elementType);
expr.WithRR(elementRR);
expr = new DirectionExpression(FieldDirection.Ref, expr); expr = new DirectionExpression(FieldDirection.Ref, expr);
return expr.WithRR(new ByReferenceResolveResult(elementType, ReferenceKind.Ref)); return expr.WithRR(new ByReferenceResolveResult(elementRR, ReferenceKind.Ref));
} }
else else
{ {
@ -1302,7 +1303,7 @@ namespace ICSharpCode.Decompiler.CSharp
.WithILInstruction(inst) .WithILInstruction(inst)
.WithRR(new ResolveResult(elementType)); .WithRR(new ResolveResult(elementType));
return new DirectionExpression(FieldDirection.Ref, expr) return new DirectionExpression(FieldDirection.Ref, expr)
.WithoutILInstruction().WithRR(new ByReferenceResolveResult(expr.Type, ReferenceKind.Ref)); .WithoutILInstruction().WithRR(new ByReferenceResolveResult(expr.ResolveResult, ReferenceKind.Ref));
} }
right = Translate(offsetInst); right = Translate(offsetInst);
right = ConvertArrayIndex(right, inst.RightInputType, allowIntPtr: true); right = ConvertArrayIndex(right, inst.RightInputType, allowIntPtr: true);
@ -2894,7 +2895,7 @@ namespace ICSharpCode.Decompiler.CSharp
{ {
var expr = ConvertField(inst.Field).WithILInstruction(inst); var expr = ConvertField(inst.Field).WithILInstruction(inst);
return new DirectionExpression(FieldDirection.Ref, expr) return new DirectionExpression(FieldDirection.Ref, expr)
.WithoutILInstruction().WithRR(new ByReferenceResolveResult(expr.Type, ReferenceKind.Ref)); .WithoutILInstruction().WithRR(new ByReferenceResolveResult(expr.ResolveResult, ReferenceKind.Ref));
} }
protected internal override TranslatedExpression VisitLdElema(LdElema inst, TranslationContext context) protected internal override TranslatedExpression VisitLdElema(LdElema inst, TranslationContext context)
@ -2922,7 +2923,7 @@ namespace ICSharpCode.Decompiler.CSharp
} }
TranslatedExpression expr = indexerExpr.WithILInstruction(inst).WithRR(new ResolveResult(arrayType.ElementType)); TranslatedExpression expr = indexerExpr.WithILInstruction(inst).WithRR(new ResolveResult(arrayType.ElementType));
return new DirectionExpression(FieldDirection.Ref, expr) return new DirectionExpression(FieldDirection.Ref, expr)
.WithoutILInstruction().WithRR(new ByReferenceResolveResult(expr.Type, ReferenceKind.Ref)); .WithoutILInstruction().WithRR(new ByReferenceResolveResult(expr.ResolveResult, ReferenceKind.Ref));
} }
TranslatedExpression TranslateArrayIndex(ILInstruction i) TranslatedExpression TranslateArrayIndex(ILInstruction i)
@ -3080,7 +3081,7 @@ namespace ICSharpCode.Decompiler.CSharp
Arguments = { Translate(inst.Argument).Expression, new TypeReferenceExpression(ConvertType(inst.Type)) } Arguments = { Translate(inst.Argument).Expression, new TypeReferenceExpression(ConvertType(inst.Type)) }
}.WithRR(new ResolveResult(inst.Type)); }.WithRR(new ResolveResult(inst.Type));
return new DirectionExpression(FieldDirection.Ref, expr.WithILInstruction(inst)).WithoutILInstruction() return new DirectionExpression(FieldDirection.Ref, expr.WithILInstruction(inst)).WithoutILInstruction()
.WithRR(new ByReferenceResolveResult(inst.Type, ReferenceKind.Ref)); .WithRR(new ByReferenceResolveResult(expr.ResolveResult, ReferenceKind.Ref));
} }
protected internal override TranslatedExpression VisitBlock(Block block, TranslationContext context) protected internal override TranslatedExpression VisitBlock(Block block, TranslationContext context)

5
ICSharpCode.Decompiler/CSharp/Transforms/IntroduceExtensionMethods.cs

@ -180,10 +180,11 @@ namespace ICSharpCode.Decompiler.CSharp.Transforms
{ {
target = new ConversionResolveResult(method.Parameters[0].Type, crr, Conversion.NullLiteralConversion); target = new ConversionResolveResult(method.Parameters[0].Type, crr, Conversion.NullLiteralConversion);
} }
else if (target is ByReferenceResolveResult brrr) else if (firstArgument is DirectionExpression de)
{ {
target = brrr.ElementResult; target = de.Expression.GetResolveResult();
} }
Debug.Assert(target != null);
ResolveResult[] args = new ResolveResult[invocationExpression.Arguments.Count - 1]; ResolveResult[] args = new ResolveResult[invocationExpression.Arguments.Count - 1];
string[] argNames = null; string[] argNames = null;
int pos = 0; int pos = 0;

5
ICSharpCode.Decompiler/Semantics/ByReferenceResolveResult.cs

@ -42,7 +42,10 @@ namespace ICSharpCode.Decompiler.Semantics
this.ElementResult = elementResult; this.ElementResult = elementResult;
} }
public ByReferenceResolveResult(IType elementType, ReferenceKind kind) /// <remarks>
/// Should only be used for temporary ResolveResults in TypeInference and CSharpConversions, etc.
/// </remarks>
internal ByReferenceResolveResult(IType elementType, ReferenceKind kind)
: base(new ByReferenceType(elementType)) : base(new ByReferenceType(elementType))
{ {
this.ReferenceKind = kind; this.ReferenceKind = kind;

Loading…
Cancel
Save