public LoadInterfaceMethodDataAction(MethodAnalysis context, Instruction instruction) : base(context, instruction) { if (context.GetConstantInReg("rcx") is {} castConstant && castConstant.Value is NewSafeCastResult castResult && context.GetConstantInReg("rdx") is {} interfaceConstant && interfaceConstant.Value is TypeDefinition interfaceType && context.GetConstantInReg("r8") is {} slotConstant && slotConstant.Value is int slot && context.Actions.FirstOrDefault(a => a is LocateSpecificInterfaceOffsetAction) is LocateSpecificInterfaceOffsetAction locator ) { _invokedOn = castResult.original; _interfaceType = interfaceType; _slotNumber = slot; resolvedMethod = SharedState.VirtualMethodsBySlot[(ushort)(locator._matchingInterfaceOffset.offset + _slotNumber)]; _resultConstant = context.MakeConstant(typeof(MethodDefinition), resolvedMethod, reg: "rax"); } }
public CallManagedFunctionInRegAction(MethodAnalysis context, Instruction instruction) : base(context, instruction) { var regName = Utils.GetRegisterNameNew(instruction.MemoryBase); var operand = context.GetConstantInReg(regName); _targetMethod = (MethodDefinition)operand.Value; if (!_targetMethod.IsStatic) { _instanceCalledOn = context.GetLocalInReg("rcx"); if (_instanceCalledOn == null) { var cons = context.GetConstantInReg("rcx"); if (cons?.Value is NewSafeCastResult castResult) { _instanceCalledOn = castResult.original; } } } }
public InterfaceOffsetsReadAction(MethodAnalysis context, Instruction instruction) : base(context, instruction) { var regName = Utils.GetRegisterNameNew(instruction.MemoryBase); var regConstant = context.GetConstantInReg(regName); _loadedFor = (Il2CppClassIdentifier)regConstant.Value; InterfaceOffsets = _loadedFor.backingType.InterfaceOffsets; _destReg = Utils.GetRegisterNameNew(instruction.Op0Register); _destinationConst = context.MakeConstant(typeof(Il2CppInterfaceOffset[]), InterfaceOffsets, reg: _destReg); }
public LocateSpecificInterfaceOffsetAction(MethodAnalysis context, Instruction instruction) : base(context, instruction) { var secondOpName = Utils.GetRegisterNameNew(instruction.Op1Register); var secondOp = context.GetConstantInReg(secondOpName); _interfaceType = (TypeDefinition)secondOp.Value; offsetReads = (InterfaceOffsetsReadAction)context.Actions.Last(a => a is InterfaceOffsetsReadAction); var cppType = SharedState.MonoToCppTypeDefs[_interfaceType]; _matchingInterfaceOffset = offsetReads.InterfaceOffsets.First(i => i.type == cppType); }
public AllocateInstanceAction(MethodAnalysis context, Instruction instruction) : base(context, instruction) { var constant = context.GetConstantInReg("rcx"); if (constant == null || constant.Type != typeof(TypeDefinition)) { return; } TypeCreated = (TypeDefinition)constant.Value; LocalReturned = context.MakeLocal(TypeCreated, reg: "rax"); }