MCPcopy Create free account
hub / github.com/FEX-Emu/FEX / DecodeInstructionImpl

Method DecodeInstructionImpl

FEXCore/Source/Interface/Core/Frontend.cpp:814–1031  ·  view source on GitHub ↗

Source from the content-addressed store, hash-verified

812}
813
814bool Decoder::DecodeInstructionImpl(uint64_t PC) {
815 InstructionSize = 0;
816 Instruction.fill(0);
817
818 DecodeInst = &DecodedBuffer[DecodedSize];
819 memset(DecodeInst, 0, sizeof(DecodedInst));
820 DecodeInst->PC = PC;
821
822 for (;;) {
823 if (InstructionSize >= MAX_INST_SIZE) {
824 return false;
825 }
826 uint8_t Op = ReadByte();
827 switch (Op) {
828 case 0x0F: { // Escape Op
829 uint8_t EscapeOp = ReadByte();
830 switch (EscapeOp) {
831 case 0x0F:
832 [[unlikely]] { // 3DNow!
833 // 3DNow! Instruction Encoding: 0F 0F [ModRM] [SIB] [Displacement] [Opcode]
834 // Decode ModRM
835 uint8_t ModRMByte = ReadByte();
836 DecodeInst->ModRM = ModRMByte;
837 DecodeInst->DecodedModRM = true;
838
839 FEXCore::X86Tables::ModRMDecoded ModRM;
840 ModRM.Hex = DecodeInst->ModRM;
841
842 const bool Has16BitAddressing = !BlockInfo.Is64BitMode && DecodeInst->Flags & DecodeFlags::FLAG_ADDRESS_SIZE;
843
844 // All 3DNow! instructions have the second argument as the rm handler
845 // We need to decode it upfront to get the displacement out of the way
846 if (ModRM.mod != 0b11) {
847 auto Disp = DecodeModRMs_Disp[Has16BitAddressing];
848 (this->*Disp)(&DecodeInst->Src[0], ModRM);
849 }
850
851 // Take a peek at the op just past the displacement
852 uint8_t LocalOp = ReadByte();
853 return NormalOpHeader(&FEXCore::X86Tables::DDDNowOps[LocalOp], LocalOp);
854 break;
855 }
856 case 0x38: { // F38 Table!
857 constexpr uint16_t PF_38_NONE = 0;
858 constexpr uint16_t PF_38_66 = (1U << 0);
859 constexpr uint16_t PF_38_F2 = (1U << 1);
860 constexpr uint16_t PF_38_F3 = (1U << 2);
861
862 uint16_t Prefix = PF_38_NONE;
863 if (DecodeInst->Flags & DecodeFlags::FLAG_OPERAND_SIZE) {
864 Prefix |= PF_38_66;
865 }
866 if (DecodeInst->Flags & DecodeFlags::FLAG_REPNE_PREFIX) {
867 Prefix |= PF_38_F2;
868 }
869 if (DecodeInst->Flags & DecodeFlags::FLAG_REP_PREFIX) {
870 Prefix |= PF_38_F3;
871 }

Callers

nothing calls this directly

Calls 3

PopOpAddrIfFunction · 0.85
PushOpAddrFunction · 0.85
IsGPRMethod · 0.45

Tested by

no test coverage detected