使用mov reg到reg创建shellcode问题>>

问题描述 投票:2回答:1

好吧,我试图创建一个创建shellcode的函数。

我在解决rex / mod东西时遇到很多问题。

我当前的代码工作方式。

到目前为止,如果regs小于R8,它将正常工作。

如果我使用一个较小的reg,那么R8可以。

问题是我必须将regs设置为小于r8,并且相同,或者如果src较小,则会出现问题

enum Reg64 : uint8_t {
    RAX = 0, RCX = 1, RDX = 2, RBX = 3,
    RSP = 4, RBP = 5, RSI = 6, RDI = 7,
    R8 = 8, R9 = 9, R10 = 10, R11 = 11,
    R12 = 12, R13 = 13, R14 = 14, R15 = 15
};

inline uint8_t encode_rex(uint8_t is_64_bit, uint8_t extend_sib_index, uint8_t extend_modrm_reg, uint8_t extend_modrm_rm) {
    struct Result {
        uint8_t b : 1;
        uint8_t x : 1;
        uint8_t r : 1;
        uint8_t w : 1;
        uint8_t fixed : 4;
    } result{ extend_modrm_rm, extend_modrm_reg, extend_sib_index, is_64_bit, 0b100 };
    return *(uint8_t*)&result;
}
inline uint8_t encode_modrm(uint8_t mod, uint8_t rm, uint8_t reg) {
    struct Result {
        uint8_t rm : 3;
        uint8_t reg : 3;
        uint8_t mod : 2;
    } result{ rm, reg, mod };
    return *(uint8_t*)&result;
}

    inline void mov(Reg64 dest, Reg64 src) {
        if (dest >= 8)
            put<uint8_t>(encode_rex(1, 2, 0, 1));
        else if (src >= 8)
            put<uint8_t>(encode_rex(1, 1, 0, 2));
        else
            put<uint8_t>(encode_rex(1, 0, 0, 0));

        put<uint8_t>(0x89);

        put<uint8_t>(encode_modrm(3, dest, src));
    }

    //c.mov(Reg64::RAX, Reg64::RAX); // works
    //c.mov(Reg64::RAX, Reg64::R9); // works
    //c.mov(Reg64::R9, Reg64::RAX); // works
    //c.mov(Reg64::R9, Reg64::R9); // Does not work returns (mov r9,rcx)

同样,如果有一个较短的方法来完成此操作,而没有所有的if,那将是很好的选择。

好吧,我试图创建一个创建shellcode的函数。我在解决rex / mod东西时遇到很多问题。我当前的代码工作正常。到目前为止,如果regs小于R8,则它...

c++ assembly x86-64 machine-code
1个回答
1
投票

FYI,大多数人通过与NASM之类的常规汇编程序进行汇编来创建Shellcode,然后将其二进制文件十六进制转储为C字符串。编写自己的汇编器可能是一个有趣的项目,但基本上是一个单独的项目。

© www.soinside.com 2019 - 2024. All rights reserved.