diff --git a/assets/InstructionEditor/Zydis.InstructionEditor.pas b/assets/InstructionEditor/Zydis.InstructionEditor.pas index 6b085ee..1c91851 100644 --- a/assets/InstructionEditor/Zydis.InstructionEditor.pas +++ b/assets/InstructionEditor/Zydis.InstructionEditor.pas @@ -1712,25 +1712,15 @@ end; procedure TX86Flags.AssignTo(Dest: TPersistent); var D: TX86Flags; + I: Integer; begin if (Dest is TX86Flags) then begin D := Dest as TX86Flags; - D.FCF := FCF; - D.FPF := FPF; - D.FAF := FAF; - D.FZF := FZF; - D.FSF := FSF; - D.FTF := FTF; - D.FIF := FIF; - D.FDF := FDF; - D.FOF := FOF; - D.FRF := FRF; - D.FVM := FVM; - D.FAC := FAC; - D.FVIF := FVIF; - D.FVIP := FVIP; - D.FID := FID; + for I := 0 to GetFlagCount - 1 do + begin + D.SetFlagValue(I, GetFlagValue(I)); + end; D.Changed; end else inherited; end; @@ -1750,11 +1740,18 @@ begin end; function TX86Flags.Equals(const Value: TX86Flags): Boolean; +var + I: Integer; begin - Result := (Value.FCF = FCF) and (Value.FPF = FPF) and (Value.FAF = FAF) and - (Value.FZF = FZF) and (Value.FSF = FSF) and (Value.FTF = FTF) and (Value.FIF = FIF) and - (Value.FDF = FDF) and (Value.FOF = FOF) and (Value.FRF = FRF) and (Value.FVM = FVM) and - (Value.FAC = FAC) and (Value.FVIF = FVIF) and (Value.FVIP = FVIP) and (Value.FID = FID); + Result := true; + for I := 0 to GetFlagCount - 1 do + begin + if (GetFlagValue(I) <> Value.GetFlagValue(I)) then + begin + Result := false; + Break; + end; + end; end; function TX86Flags.GetConflictState: Boolean; @@ -1765,6 +1762,8 @@ var RegsWrite: TX86RegisterSet; R: TX86Register; begin + Exit(false); + Result := false; RegsRead := []; RegsWrite := []; @@ -2472,7 +2471,11 @@ begin Result := true; for I := Low(FOperands) to High(FOperands) do begin - Result := Result and Value.FOperands[I].Equals(FOperands[I]); + if (not Value.FOperands[I].Equals(FOperands[I])) then + begin + Result := false; + Break; + end; end; end; diff --git a/include/Zydis/Formatter.h b/include/Zydis/Formatter.h index 3406f2c..3bf3a57 100644 --- a/include/Zydis/Formatter.h +++ b/include/Zydis/Formatter.h @@ -233,7 +233,7 @@ enum ZydisFormatterHookTypes * @brief This function is called to format an memory operand. * * Replacing this function might indirectly disable some specific calls to the - * @c ZYDIS_FORMATTER_PRINT_ADDRESS function. + * @c ZYDIS_FORMATTER_PRINT_ADDRESS and @c ZYDIS_FORMATTER_HOOK_PRINT_DISPLACEMENT functions. */ ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_MEM, /** @@ -244,7 +244,7 @@ enum ZydisFormatterHookTypes * @brief This function is called to format an immediate operand. * * Replacing this function might indirectly disable some specific calls to the - * @c ZYDIS_FORMATTER_PRINT_ADDRESS function. + * @c ZYDIS_FORMATTER_PRINT_ADDRESS and @c ZYDIS_FORMATTER_HOOK_PRINT_IMMEDIATE functions. */ ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_IMM, /** @@ -262,10 +262,18 @@ enum ZydisFormatterHookTypes * avx-512 operand decorator. */ ZYDIS_FORMATTER_HOOK_PRINT_DECORATOR, - /** + /** * @brief This function is called to print an absolute address. */ - ZYDIS_FORMATTER_HOOK_PRINT_ADDRESS + ZYDIS_FORMATTER_HOOK_PRINT_ADDRESS, + /** + * @brief This function is called to print a memory displacement value. + */ + ZYDIS_FORMATTER_HOOK_PRINT_DISPLACEMENT, + /** + * @brief This function is called to print an immediate value. + */ + ZYDIS_FORMATTER_HOOK_PRINT_IMMEDIATE }; /* ---------------------------------------------------------------------------------------------- */ @@ -336,7 +344,9 @@ typedef ZydisStatus (*ZydisFormatterFormatFunc)(ZydisInstructionFormatter* forma * This function type is used for the @c ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_REG, * @c ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_MEM, @c ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_PTR, * @c ZYDIS_FORMATTER_HOOK_FORMAT_OPERAND_IMM, @c ZYDIS_FORMATTER_HOOK_PRINT_OPERANDSIZE, - * @c ZYDIS_FORMATTER_HOOK_PRINT_SEGMENT and @c ZYDIS_FORMATTER_HOOK_PRINT_DECORATOR hook-types. + * @c ZYDIS_FORMATTER_HOOK_PRINT_SEGMENT, @c ZYDIS_FORMATTER_HOOK_PRINT_DECORATOR, + * @c ZYDIS_FORMATTER_HOOK_PRINT_DISPLACEMENT and @c ZYDIS_FORMATTER_HOOK_PRINT_IMMEDIATE + * hook-types. */ typedef ZydisStatus (*ZydisFormatterFormatOperandFunc)(ZydisInstructionFormatter* formatter, char** buffer, size_t bufferLen, ZydisInstructionInfo* info, ZydisOperandInfo* operand); @@ -385,6 +395,8 @@ typedef struct ZydisInstructionFormatter_ ZydisFormatterFormatOperandFunc funcPrintSegment; ZydisFormatterFormatOperandFunc funcPrintDecorator; ZydisFormatterFormatAddressFunc funcPrintAddress; + ZydisFormatterFormatOperandFunc funcPrintDisplacement; + ZydisFormatterFormatOperandFunc funcPrintImmediate; const char* prefixHEX; const char* prefixOCT; const char* delimMnemonic; diff --git a/src/Formatter.c b/src/Formatter.c index ca50f72..00b3759 100644 --- a/src/Formatter.c +++ b/src/Formatter.c @@ -332,29 +332,8 @@ static ZydisStatus ZydisFormatterFormatOperandMemIntel(ZydisInstructionFormatter ZYDIS_STRBUF_APPEND_MODE_DEFAULT, "*%d", operand->mem.scale)); } } - if ((operand->mem.disp.dataSize) && ((operand->mem.disp.value.sqword) || - ((operand->mem.base == ZYDIS_REGISTER_NONE) && - (operand->mem.index == ZYDIS_REGISTER_NONE)))) - { - bool printSignedHEX = - (formatter->displacementFormat != ZYDIS_FORMATTER_DISP_HEX_UNSIGNED); - if (printSignedHEX && (operand->mem.disp.value.sqword < 0) && ( - (operand->mem.base != ZYDIS_REGISTER_NONE) || - (operand->mem.index != ZYDIS_REGISTER_NONE))) - { - ZYDIS_CHECK(ZydisStringBufferAppendFormat(buffer, bufEnd - *buffer, - ZYDIS_STRBUF_APPEND_MODE_DEFAULT, - "-0x%02"PRIX32, -operand->mem.disp.value.sdword)); - } else - { - const char* sign = - ((operand->mem.base == ZYDIS_REGISTER_NONE) && - (operand->mem.index == ZYDIS_REGISTER_NONE)) ? "" : "+"; - ZYDIS_CHECK(ZydisStringBufferAppendFormat(buffer, bufEnd - *buffer, - ZYDIS_STRBUF_APPEND_MODE_DEFAULT, - "%s0x%02"PRIX32, sign, operand->mem.disp.value.sdword)); - } - } + ZYDIS_CHECK(formatter->funcPrintDisplacement(formatter, buffer, bufEnd - *buffer, + info, operand)); } return ZydisStringBufferAppend(buffer, bufEnd - *buffer, ZYDIS_STRBUF_APPEND_MODE_DEFAULT, "]"); @@ -380,10 +359,10 @@ static ZydisStatus ZydisFormatterFormatOperandImmIntel(ZydisInstructionFormatter return ZYDIS_STATUS_INVALID_PARAMETER; } - bool printSignedHEX = false; // The immediate operand contains an address if (operand->imm.isRelative) { + bool printSignedHEX = false; switch (formatter->addressFormat) { case ZYDIS_FORMATTER_ADDR_DEFAULT: @@ -412,7 +391,70 @@ static ZydisStatus ZydisFormatterFormatOperandImmIntel(ZydisInstructionFormatter } // The immediate operand contains an actual ordinal value - printSignedHEX = (formatter->immediateFormat == ZYDIS_FORMATTER_IMM_HEX_SIGNED); + return formatter->funcPrintImmediate(formatter, buffer, bufferLen, info, operand); +} + +/* ---------------------------------------------------------------------------------------------- */ + +static ZydisStatus ZydisFormatterPrintAddressIntel(ZydisInstructionFormatter* formatter, + char** buffer, size_t bufferLen, ZydisInstructionInfo* info, ZydisOperandInfo* operand, + uint64_t address) +{ + if (!formatter || !buffer || !*buffer || (bufferLen <= 0) || !info || !operand) + { + return ZYDIS_STATUS_INVALID_PARAMETER; + } + + switch (info->mode) + { + case ZYDIS_DISASSEMBLER_MODE_16BIT: + case ZYDIS_DISASSEMBLER_MODE_32BIT: + return ZydisStringBufferAppendFormat(buffer, bufferLen, ZYDIS_STRBUF_APPEND_MODE_DEFAULT, + "0x%08"PRIX64, address); + case ZYDIS_DISASSEMBLER_MODE_64BIT: + return ZydisStringBufferAppendFormat(buffer, bufferLen, ZYDIS_STRBUF_APPEND_MODE_DEFAULT, + "0x%016"PRIX64, address); + default: + return ZYDIS_STATUS_INVALID_PARAMETER; + } +} + +static ZydisStatus ZydisFormatterPrintDisplacementIntel(ZydisInstructionFormatter* formatter, + char** buffer, size_t bufferLen, ZydisInstructionInfo* info, ZydisOperandInfo* operand) +{ + if (!formatter || !buffer || !*buffer || (bufferLen <= 0) || !info || !operand) + { + return ZYDIS_STATUS_INVALID_PARAMETER; + } + if ((operand->mem.disp.dataSize) && ((operand->mem.disp.value.sqword) || + ((operand->mem.base == ZYDIS_REGISTER_NONE) && + (operand->mem.index == ZYDIS_REGISTER_NONE)))) + { + bool printSignedHEX = (formatter->displacementFormat != ZYDIS_FORMATTER_DISP_HEX_UNSIGNED); + if (printSignedHEX && (operand->mem.disp.value.sqword < 0) && ( + (operand->mem.base != ZYDIS_REGISTER_NONE) || + (operand->mem.index != ZYDIS_REGISTER_NONE))) + { + return ZydisStringBufferAppendFormat(buffer, bufferLen, + ZYDIS_STRBUF_APPEND_MODE_DEFAULT, "-0x%02"PRIX32, -operand->mem.disp.value.sdword); + } + } + const char* sign = + ((operand->mem.base == ZYDIS_REGISTER_NONE) && + (operand->mem.index == ZYDIS_REGISTER_NONE)) ? "" : "+"; + return ZydisStringBufferAppendFormat(buffer, bufferLen, ZYDIS_STRBUF_APPEND_MODE_DEFAULT, + "%s0x%02"PRIX32, sign, operand->mem.disp.value.sdword); +} + +static ZydisStatus ZydisFormatterPrintImmediateIntel(ZydisInstructionFormatter* formatter, + char** buffer, size_t bufferLen, ZydisInstructionInfo* info, ZydisOperandInfo* operand) +{ + if (!formatter || !buffer || !*buffer || (bufferLen <= 0) || !info || !operand) + { + return ZYDIS_STATUS_INVALID_PARAMETER; + } + + bool printSignedHEX = (formatter->immediateFormat == ZYDIS_FORMATTER_IMM_HEX_SIGNED); if (formatter->immediateFormat == ZYDIS_FORMATTER_IMM_HEX_AUTO) { printSignedHEX = operand->imm.isSigned; @@ -458,29 +500,6 @@ static ZydisStatus ZydisFormatterFormatOperandImmIntel(ZydisInstructionFormatter /* ---------------------------------------------------------------------------------------------- */ -static ZydisStatus ZydisFormatterPrintAddressIntel(ZydisInstructionFormatter* formatter, - char** buffer, size_t bufferLen, ZydisInstructionInfo* info, ZydisOperandInfo* operand, - uint64_t address) -{ - if (!formatter || !buffer || !*buffer || (bufferLen <= 0) || !info || !operand) - { - return ZYDIS_STATUS_INVALID_PARAMETER; - } - - switch (info->mode) - { - case ZYDIS_DISASSEMBLER_MODE_16BIT: - case ZYDIS_DISASSEMBLER_MODE_32BIT: - return ZydisStringBufferAppendFormat(buffer, bufferLen, ZYDIS_STRBUF_APPEND_MODE_DEFAULT, - "0x%08"PRIX64, address); - case ZYDIS_DISASSEMBLER_MODE_64BIT: - return ZydisStringBufferAppendFormat(buffer, bufferLen, ZYDIS_STRBUF_APPEND_MODE_DEFAULT, - "0x%016"PRIX64, address); - default: - return ZYDIS_STATUS_INVALID_PARAMETER; - } -} - static ZydisStatus ZydisFormatterPrintOperandSizeIntel(ZydisInstructionFormatter* formatter, char** buffer, size_t bufferLen, ZydisInstructionInfo* info, ZydisOperandInfo* operand) { @@ -836,6 +855,8 @@ ZydisStatus ZydisFormatterInitInstructionFormatterEx( formatter->funcPrintSegment = &ZydisFormatterPrintSegmentIntel; formatter->funcPrintDecorator = &ZydisFormatterPrintDecoratorIntel; formatter->funcPrintAddress = &ZydisFormatterPrintAddressIntel; + formatter->funcPrintDisplacement = &ZydisFormatterPrintDisplacementIntel; + formatter->funcPrintImmediate = &ZydisFormatterPrintImmediateIntel; break; default: return ZYDIS_STATUS_INVALID_PARAMETER; @@ -896,6 +917,12 @@ ZydisStatus ZydisFormatterSetHook(ZydisInstructionFormatter* formatter, case ZYDIS_FORMATTER_HOOK_PRINT_ADDRESS: *callback = *(const void**)&formatter->funcPrintAddress; break; + case ZYDIS_FORMATTER_HOOK_PRINT_DISPLACEMENT: + *callback = *(const void**)&formatter->funcPrintDisplacement; + break; + case ZYDIS_FORMATTER_HOOK_PRINT_IMMEDIATE: + *callback = *(const void**)&formatter->funcPrintImmediate; + break; default: return ZYDIS_STATUS_INVALID_PARAMETER; } @@ -945,9 +972,15 @@ ZydisStatus ZydisFormatterSetHook(ZydisInstructionFormatter* formatter, case ZYDIS_FORMATTER_HOOK_PRINT_DECORATOR: formatter->funcPrintDecorator = *(ZydisFormatterFormatOperandFunc*)&temp; break; - case ZYDIS_FORMATTER_HOOK_PRINT_ADDRESS: + case ZYDIS_FORMATTER_HOOK_PRINT_ADDRESS: formatter->funcPrintAddress = *(ZydisFormatterFormatAddressFunc*)&temp; break; + case ZYDIS_FORMATTER_HOOK_PRINT_DISPLACEMENT: + formatter->funcPrintDisplacement = *(ZydisFormatterFormatOperandFunc*)&temp; + break; + case ZYDIS_FORMATTER_HOOK_PRINT_IMMEDIATE: + formatter->funcPrintImmediate = *(ZydisFormatterFormatOperandFunc*)&temp; + break; default: break; }