Browse Source

Fix #296: Array initialization decompiles into recursive reference

pull/320/merge
Daniel Grunwald 14 years ago
parent
commit
0b968182a3
  1. 11
      ICSharpCode.Decompiler/ILAst/ILAstOptimizer.cs
  2. 4
      ICSharpCode.Decompiler/ILAst/InitializerPeepholeTransforms.cs
  3. 16
      ICSharpCode.Decompiler/Tests/InitializerTests.cs
  4. 2
      ILSpy/TextView/DecompilerTextView.cs

11
ICSharpCode.Decompiler/ILAst/ILAstOptimizer.cs

@ -851,5 +851,16 @@ namespace ICSharpCode.Decompiler.ILAst
if (!collection.Remove(key)) if (!collection.Remove(key))
throw new Exception("The key was not found in the dictionary"); throw new Exception("The key was not found in the dictionary");
} }
public static bool ContainsReferenceTo(this ILExpression expr, ILVariable v)
{
if (expr.Operand == v)
return true;
foreach (var arg in expr.Arguments) {
if (ContainsReferenceTo(arg, v))
return true;
}
return false;
}
} }
} }

4
ICSharpCode.Decompiler/ILAst/InitializerPeepholeTransforms.cs

@ -63,7 +63,9 @@ namespace ICSharpCode.Decompiler.ILAst
v == v3 && v == v3 &&
nextExpr.Arguments[1].Match(ILCode.Ldc_I4, out arrayPos) && nextExpr.Arguments[1].Match(ILCode.Ldc_I4, out arrayPos) &&
arrayPos >= operands.Count && arrayPos >= operands.Count &&
arrayPos <= operands.Count + maxConsecutiveDefaultValueExpressions) { arrayPos <= operands.Count + maxConsecutiveDefaultValueExpressions &&
!nextExpr.Arguments[2].ContainsReferenceTo(v3))
{
while (operands.Count < arrayPos) while (operands.Count < arrayPos)
operands.Add(new ILExpression(ILCode.DefaultValue, elementType)); operands.Add(new ILExpression(ILCode.DefaultValue, elementType));
operands.Add(nextExpr.Arguments[2]); operands.Add(nextExpr.Arguments[2]);

16
ICSharpCode.Decompiler/Tests/InitializerTests.cs

@ -353,6 +353,15 @@ public class InitializerTests
InitializerTests.MyEnum.b InitializerTests.MyEnum.b
}); });
} }
public static void RecursiveArrayInitializer()
{
int[] array = new int[3];
array[0] = 1;
array[1] = 2;
array[2] = array[1] + 1;
array[0] = 0;
}
#endregion #endregion
public static void CollectionInitializerList() public static void CollectionInitializerList()
@ -365,6 +374,13 @@ public class InitializerTests
}); });
} }
public static object RecursiveCollectionInitializer()
{
List<object> list = new List<object>();
list.Add(list);
return list;
}
public static void CollectionInitializerDictionary() public static void CollectionInitializerDictionary()
{ {
InitializerTests.X(InitializerTests.Y(), new Dictionary<string, int> InitializerTests.X(InitializerTests.Y(), new Dictionary<string, int>

2
ILSpy/TextView/DecompilerTextView.cs

@ -727,7 +727,7 @@ namespace ICSharpCode.ILSpy.TextView
output.AddButton(null, "Open Explorer", delegate { Process.Start("explorer", "/select,\"" + fileName + "\""); }); output.AddButton(null, "Open Explorer", delegate { Process.Start("explorer", "/select,\"" + fileName + "\""); });
output.WriteLine(); output.WriteLine();
tcs.SetResult(output); tcs.SetResult(output);
} catch (OperationCanceledException ex) { } catch (OperationCanceledException) {
tcs.SetCanceled(); tcs.SetCanceled();
#if DEBUG #if DEBUG
} catch (AggregateException ex) { } catch (AggregateException ex) {

Loading…
Cancel
Save