public void ReadFunction(uint RAMAddr, uint RAMtoROM, ref StructList <Instruction> instructions) { instructions.Clear(); Instruction cur; ROM rom = ROM.Instance; uint ROM_OFFSET = RAMAddr - RAMtoROM; uint offset = ROM_OFFSET; int end = 0x8000; while (end > 0) { cur = parseInstruction(rom.readWordUnsigned(offset)); offset += 4; end--; if (cur.opCode == OPCODE.JR && cur.gp_1 == GP_REGISTER.RA) { end = 1; } instructions.Add(ref cur); } }
public void findJALsInFunction(uint RAMFunc, uint RAMtoROM, ref StructList <JAL_CALL> calls) { calls.Clear(); StructList <Instruction> inst_list = new StructList <Instruction>(); Instruction inst = default(Instruction); ReadFunction(RAMFunc, RAMtoROM, ref inst_list); JAL_CALL jal = default(JAL_CALL); bool addNextTime = false; while (inst_list.Dequeue(ref inst)) { bool addJAL = addNextTime; switch (inst.opCode) { case OPCODE.LUI: if (inst.gp_dest == GP_REGISTER.A0) { jal.a0 = (uint)(inst.immediate << 16); } else if (inst.gp_dest == GP_REGISTER.A1) { jal.a1 = (uint)(inst.immediate << 16); } else if (inst.gp_dest == GP_REGISTER.A2) { jal.a2 = (uint)(inst.immediate << 16); } else if (inst.gp_dest == GP_REGISTER.A3) { jal.a3 = (uint)(inst.immediate << 16); } break; case OPCODE.ADDIU: if (inst.gp_dest == GP_REGISTER.A0 && inst.gp_1 == GP_REGISTER.A0) { jal.a0 += (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A1 && inst.gp_1 == GP_REGISTER.A1) { jal.a1 += (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A2 && inst.gp_1 == GP_REGISTER.A2) { jal.a2 += (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A3 && inst.gp_1 == GP_REGISTER.A3) { jal.a3 += (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A0 && inst.gp_1 == GP_REGISTER.R0) { jal.a0 = (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A1 && inst.gp_1 == GP_REGISTER.R0) { jal.a1 = (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A2 && inst.gp_1 == GP_REGISTER.R0) { jal.a2 = (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A3 && inst.gp_1 == GP_REGISTER.R0) { jal.a3 = (uint)inst.immediate; } break; case OPCODE.ORI: if (inst.gp_dest == GP_REGISTER.A0 && inst.gp_1 == GP_REGISTER.A0) { jal.a0 |= (ushort)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A1 && inst.gp_1 == GP_REGISTER.A1) { jal.a1 |= (ushort)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A2 && inst.gp_1 == GP_REGISTER.A2) { jal.a2 |= (ushort)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A3 && inst.gp_1 == GP_REGISTER.A3) { jal.a3 |= (ushort)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A0 && inst.gp_1 == GP_REGISTER.R0) { jal.a0 = (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A1 && inst.gp_1 == GP_REGISTER.R0) { jal.a1 = (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A2 && inst.gp_1 == GP_REGISTER.R0) { jal.a2 = (uint)inst.immediate; } else if (inst.gp_dest == GP_REGISTER.A3 && inst.gp_1 == GP_REGISTER.R0) { jal.a3 = (uint)inst.immediate; } break; case OPCODE.JAL: jal.JAL_ADDRESS = inst.jump_to_func; addNextTime = true; break; } if (addJAL) { calls.Add(ref jal); //Console.WriteLine(newCall.ToString()); addNextTime = false; } } }