Browse Source

Get type of elements obtained from array

pull/1/head^2
David Srbecký 18 years ago
parent
commit
970706161a
  1. 2
      src/AstMetodBodyBuilder.cs
  2. 8
      src/StackAnalysis.Types.cs
  3. 21
      src/StackAnalysis.cs

2
src/AstMetodBodyBuilder.cs

@ -53,7 +53,7 @@ namespace Decompiler @@ -53,7 +53,7 @@ namespace Decompiler
args);
if (codeExpr is Ast.Expression) {
if (Util.GetNumberOfOutputs(methodDef, instr) == 1) {
string type = stackAnalysis.StackAfter[instr].Peek(1).Type.FullName;
string type = stackAnalysis.GetTypeOf(instr).FullName;
string name = string.Format("expr{0:X2}", instr.Offset);
Ast.LocalVariableDeclaration astLocal = new Ast.LocalVariableDeclaration(new Ast.TypeReference(type.ToString()));
astLocal.Variables.Add(new Ast.VariableDeclaration(name, (Ast.Expression)codeExpr));

8
src/StackAnalysis.Types.cs

@ -12,6 +12,7 @@ namespace Decompiler @@ -12,6 +12,7 @@ namespace Decompiler
{
public partial class StackAnalysis
{
static public Cecil.TypeReference TypeVoid = GetCecilType(typeof(void));
static public Cecil.TypeReference TypeObject = GetCecilType(typeof(Object));
static public Cecil.TypeReference TypeBool = GetCecilType(typeof(bool));
static public Cecil.TypeReference TypeInt32 = GetCecilType(typeof(Int32));
@ -81,8 +82,13 @@ namespace Decompiler @@ -81,8 +82,13 @@ namespace Decompiler
case Code.Ldelem_U2:
case Code.Ldelem_U4:
case Code.Ldelem_R4:
case Code.Ldelem_R8:
case Code.Ldelem_R8: throw new NotImplementedException();
case Code.Ldelem_Ref:
if (arg1 is ArrayType) {
return ((ArrayType)arg1).ElementType;
} else {
throw new NotImplementedException();
}
case Code.Ldelem_Any:
case Code.Ldelema: throw new NotImplementedException();

21
src/StackAnalysis.cs

@ -63,9 +63,11 @@ namespace Decompiler @@ -63,9 +63,11 @@ namespace Decompiler
return new CilStack(this);
}
public void PopCount(int count)
public CilStackSlot[] PopCount(int count)
{
CilStackSlot[] poped = this.GetRange(this.Count - count, count).ToArray();
this.RemoveRange(this.Count - count, count);
return poped;
}
public void Push(CilStackSlot slot)
@ -115,6 +117,15 @@ namespace Decompiler @@ -115,6 +117,15 @@ namespace Decompiler
get { return stackAfter; }
}
public Cecil.TypeReference GetTypeOf(Instruction inst)
{
if (Util.GetNumberOfOutputs(methodDef, inst) == 0) {
return TypeVoid;
} else {
return StackAfter[inst].Peek(1).Type;
}
}
public StackAnalysis(MethodDefinition methodDef) {
this.methodDef = methodDef;
@ -156,9 +167,13 @@ namespace Decompiler @@ -156,9 +167,13 @@ namespace Decompiler
CilStack ChangeStack(CilStack oldStack, Instruction inst)
{
CilStack newStack = oldStack.Clone();
newStack.PopCount(Util.GetNumberOfInputs(methodDef, inst));
CilStackSlot[] popedSlots = newStack.PopCount(Util.GetNumberOfInputs(methodDef, inst));
List<Cecil.TypeReference> typeArgs = new List<Cecil.TypeReference>();
foreach(CilStackSlot slot in popedSlots) {
typeArgs.Add(slot.Type);
}
for (int i = 0; i < Util.GetNumberOfOutputs(methodDef, inst); i++) {
newStack.Push(new CilStackSlot(inst, GetType(methodDef, inst)));
newStack.Push(new CilStackSlot(inst, GetType(methodDef, inst, typeArgs.ToArray())));
}
return newStack;
}

Loading…
Cancel
Save