예제 #1
0
        public static byte[] getInitializedArray(int arraySize, MethodDefinition method, ref int newarrIndex)
        {
            var resultValueArray = new Value[arraySize];

            var emulator = new InstructionEmulator(method.HasThis, false, method.Parameters, method.Body.Variables);
            var theArray = new UnknownValue();
            emulator.push(theArray);

            var instructions = method.Body.Instructions;
            int i;
            for (i = newarrIndex + 1; i < instructions.Count; i++) {
                var instr = instructions[i];
                if (instr.OpCode.FlowControl != FlowControl.Next)
                    break;
                if (instr.OpCode.Code == Code.Newarr)
                    break;

                if (instr.OpCode.Code == Code.Stelem_I1) {
                    var value = emulator.pop();
                    var index = emulator.pop() as Int32Value;
                    var array = emulator.pop();
                    if (ReferenceEquals(array, theArray) && index != null && index.allBitsValid()) {
                        if (0 <= index.value && index.value < resultValueArray.Length)
                            resultValueArray[index.value] = value;
                    }
                }
                else
                    emulator.emulate(instr);
            }
            if (i != newarrIndex + 1)
                i--;
            newarrIndex = i;

            byte[] resultArray = new byte[resultValueArray.Length];
            for (i = 0; i < resultArray.Length; i++) {
                var intValue = resultValueArray[i] as Int32Value;
                if (intValue == null || !intValue.allBitsValid())
                    return null;
                resultArray[i] = (byte)intValue.value;
            }

            return resultArray;
        }
예제 #2
0
        // Switch deobfuscation when block uses stloc N, ldloc N to load switch constant
        //	blk1:
        //		ldc.i4 X
        //		br swblk
        //	swblk:
        //		stloc N
        //		ldloc N
        //		switch (......)
        bool deobfuscateStLdloc(IList <Block> switchTargets, Block switchFallThrough, Block block)
        {
            bool changed = false;

            foreach (var source in new List <Block>(block.Sources))
            {
                if (!isBranchBlock(source))
                {
                    continue;
                }
                instructionEmulator.init(blocks);
                instructionEmulator.emulate(source.Instructions);

                var target = getSwitchTarget(switchTargets, switchFallThrough, instructionEmulator.pop());
                if (target == null)
                {
                    continue;
                }
                source.replaceLastNonBranchWithBranch(0, target);
                source.add(new Instr(OpCodes.Pop.ToInstruction()));
                changed = true;
            }
            return(changed);
        }
예제 #3
0
		bool emulate_Beq() {
			var val2 = instructionEmulator.pop();
			var val1 = instructionEmulator.pop();

			if (val1.isInt32() && val2.isInt32())
				return emulateBranch(2, Int32Value.compareEq((Int32Value)val1, (Int32Value)val2));
			else if (val1.isInt64() && val2.isInt64())
				return emulateBranch(2, Int64Value.compareEq((Int64Value)val1, (Int64Value)val2));
			else if (val1.isNull() && val2.isNull())
				return emulateBranch(2, true);
			else
				return false;
		}
예제 #4
0
        public static Value[] getInitializedArray(int arraySize, MethodDef method, ref int newarrIndex, Code stelemOpCode)
        {
            var resultValueArray = new Value[arraySize];

            var emulator = new InstructionEmulator(method);
            var theArray = new UnknownValue();
            emulator.push(theArray);

            var instructions = method.Body.Instructions;
            int i;
            for (i = newarrIndex + 1; i < instructions.Count; i++) {
                var instr = instructions[i];
                if (instr.OpCode.FlowControl != FlowControl.Next)
                    break;
                if (instr.OpCode.Code == Code.Newarr)
                    break;
                switch (instr.OpCode.Code) {
                case Code.Newarr:
                case Code.Newobj:
                    goto done;

                case Code.Stloc:
                case Code.Stloc_S:
                case Code.Stloc_0:
                case Code.Stloc_1:
                case Code.Stloc_2:
                case Code.Stloc_3:
                case Code.Starg:
                case Code.Starg_S:
                case Code.Stsfld:
                case Code.Stfld:
                    if (emulator.peek() == theArray && i != newarrIndex + 1 && i != newarrIndex + 2)
                        goto done;
                    break;
                }

                if (instr.OpCode.Code == stelemOpCode) {
                    var value = emulator.pop();
                    var index = emulator.pop() as Int32Value;
                    var array = emulator.pop();
                    if (ReferenceEquals(array, theArray) && index != null && index.allBitsValid()) {
                        if (0 <= index.value && index.value < resultValueArray.Length)
                            resultValueArray[index.value] = value;
                    }
                }
                else
                    emulator.emulate(instr);
            }
            done:
            if (i != newarrIndex + 1)
                i--;
            newarrIndex = i;

            return resultValueArray;
        }