static private int FixupCallStructReturn(TypeSig returnType, List <StackEntry> arguments, IILImporterProxy importer, bool hasThis) { // Create temp var lclNum = importer.GrabTemp(returnType.GetStackValueKind(), returnType.GetExactSize()); var returnBufferPtr = new LocalVariableAddressEntry(lclNum); // Ensure return buffer parameter goes after the this parameter if present var returnBufferArgPos = hasThis ? 1 : 0; arguments.Insert(returnBufferArgPos, returnBufferPtr); return(lclNum); }
public void Import(Instruction instruction, ImportContext context, IILImporterProxy importer) { var fieldDefOrRef = instruction.Operand as IField; var fieldDef = fieldDefOrRef.ResolveFieldDef(); // Ensure fields have all offsets calculated if (fieldDef.FieldOffset == null) { fieldDef.DeclaringType.ToTypeSig().GetExactSize(); } var fieldOffset = fieldDef.FieldOffset ?? 0; var obj = importer.PopExpression(); if (obj.Kind == StackValueKind.ValueType) { if (obj is LocalVariableEntry) { obj = new LocalVariableAddressEntry((obj.As <LocalVariableEntry>()).LocalNumber); } else if (obj is IndirectEntry) { // If the object is itself an IndirectEntry e.g. resulting from a Ldfld // then we should merge the Ldfld's together // e.g. Ldfld SimpleVector::N // Ldfld Nested::Length // will get converted into a single IndirectEntry node with the field offset // being the combination of the field offsets for N and Length var previousIndirect = obj.As <IndirectEntry>(); fieldOffset = previousIndirect.Offset + fieldOffset; obj = previousIndirect.Op1; } } if (obj.Kind != StackValueKind.ObjRef && obj.Kind != StackValueKind.ByRef && obj.Kind != StackValueKind.NativeInt) { throw new NotImplementedException($"LoadFieldImporter does not support {obj.Kind}"); } var kind = fieldDef.FieldType.GetStackValueKind(); var node = new IndirectEntry(obj, kind, fieldDef.FieldType.GetExactSize(), fieldOffset); importer.PushExpression(node); }
public void Import(Instruction instruction, ImportContext context, IILImporterProxy importer) { var methodDefOrRef = instruction.Operand as IMethodDefOrRef; var methodToCall = methodDefOrRef.ResolveMethodDefThrow(); var declType = methodToCall.DeclaringType; var objType = declType.ToTypeSig(); var objKind = objType.GetStackValueKind(); var objSize = objType.GetExactSize(); if (declType.IsValueType) { // Allocate memory on the stack for the value type as a temp local variable var lclNum = importer.GrabTemp(objKind, objSize); var newObjThisPtr = new LocalVariableAddressEntry(lclNum); // Call the valuetype constructor CallImporter.ImportCall(instruction, context, importer, newObjThisPtr); var node = new LocalVariableEntry(lclNum, objKind, objSize); importer.PushExpression(node); } else { // Allocate memory for object var op1 = new AllocObjEntry((int)declType.ClassSize, objKind); // Store allocated memory address into a temp local variable var lclNum = importer.GrabTemp(objKind, objSize); var asg = new StoreLocalVariableEntry(lclNum, false, op1); importer.ImportAppendTree(asg); // Call the constructor var newObjThisPtr = new LocalVariableEntry(lclNum, objKind, objSize); CallImporter.ImportCall(instruction, context, importer, newObjThisPtr); // Push a local variable entry corresponding to the object here var node = new LocalVariableEntry(lclNum, objKind, objSize); importer.PushExpression(node); } }
public void Import(Instruction instruction, ImportContext context, IILImporterProxy importer) { var op2 = importer.PopExpression().As <Int32ConstantEntry>(); if (op2.Kind != StackValueKind.Int32) { throw new NotSupportedException("Localloc requires int size"); } var allocSize = op2.Value; // Ensure we don't allocate less than each stack entry size allocSize = RoundUp(allocSize, 4); // TODO: Is Unknown the right kind to use?? var lclNum = importer.GrabTemp(StackValueKind.Unknown, allocSize); var op1 = new LocalVariableAddressEntry(lclNum); importer.PushExpression(op1); }
public void Visit(LocalVariableAddressEntry entry) { _sb.AppendLine($"t{entry.TreeID,-3} = lclVarAddr {entry.Kind} V{entry.LocalNumber}"); }
public void Visit(LocalVariableAddressEntry entry) { _genericStackEntryVisitor.Visit <LocalVariableAddressEntry>(entry); }
public void Visit(LocalVariableAddressEntry entry) { SetNext(entry); }
public void Visit(LocalVariableAddressEntry entry) { Print($"LCL_VAR_ADDR V{entry.LocalNumber}"); }