将输入视为十六进制值

时间:2014-02-19 01:44:41

标签: c buffer-overflow shellcode

我正在尝试学习如何创建shellcode,我需要输入一大堆十六进制代码。但是,当我给我的程序输入十六进制代码时,十六进制代码被视为普通的ASCII字符,反斜杠只是被剥离。

示例:

./ a.out“AAAAAAAAAAAAAAAAAAAAAAAAAAAAAAAA \ x35 \ x85 \ x04 \ x08”

在这种情况下,十六进制代码(\ x35 \ x85 \ x04 \ x08)被视为单个字符 - 即x = 0x75等。

我的程序处理输入的方式类似于以下内容:

int authentication(char *pass){
  char password_buffer[16];
  strcpy(password_buffer, pass);
  return 1;
}

int main(int argc, char *argv[]){
   if(authentication(argv[1])){
      //access
   }
  return 1;
}

strcpy()之后从内存中转储:

0xbffff260: 0x41414141  0x41414141  0x41414141  0x41414141
0xbffff270: 0x78353378  0x30783538  0x38307834  0x08048400

如您所见,在地址0xbffff270处,内存值为0x78353378,对应于x35x,因此是十六进制代码输入中的三个首字母。我希望这四个字节为0x08048535。

如何格式化输入以执行此操作?

2 个答案:

答案 0 :(得分:2)

你可以像这样使用shell printf函数:

./a.out "$(printf "AAAAA\x08\x32\x20\xfa\x10\x16")"

十六进制值将转换为“二进制”。


这部分可能只是增加了混乱,我可以而且可能会删除它:

此外,您还可以在程序内部进行快速转换,以便更轻松地跨平台和系统使用。原油样品。 (这需要一个字符串并转换它们显示为\xNN的任何十六进制序列,并在完成时打印十六进制转储):

#include <stdio.h>
#include <stdlib.h>
#include <ctype.h>
#include <string.h>

/*
 * Hex Dump
 * */
static void txt(unsigned char *buf, int len) 
{
        int i;
        fprintf(stdout, "  ");
        for (i = 0; i < len; ++i) {
                fprintf(stdout,
                        "%c",
                        isprint(buf[i]) ?
                        buf[i] :
                        '.'
                );
        }
}

static void xxd(unsigned char *buf, int len) 
{
        int i, j;

        for (i = 0; i < len; ) {
                if (!(i % 16)) {
                        fprintf(stdout,
                                "%s%03x: ",
                                i ? "\n" : "",
                                i
                        );
                }
                fprintf(stdout, "%02x ", buf[i]);
                if (!(++i % 16))
                        txt(&buf[i - 16], 16);
        }
        if ((i % 16)) {
                for (j = i; j % 16; ++j)
                        fprintf(stdout, "   ");
                txt(&buf[i - (i % 16)], i % 16);
        }
        fprintf(stdout, "\n");
}

/*
 * Hex char to value.
 * */
static unsigned hexval(char c)
{
    if (c >= '0' && c <= '9')
        return c - '0';
    if (c >= 'a' && c <= 'f')
        return c - 'a' + 10;
    if (c >= 'A' && c <= 'F')
        return c - 'A' + 10;
    return ~0;
}
/*
 * Convert all hex sequences.
 * */
int str2bin(char *data, unsigned char **buf_ptr) 
{
        int len, converted = 0;
        unsigned int val;
        unsigned char *buf;

        buf = malloc(strlen(data) + 1);
        *buf_ptr = buf;

        for (; *data; ) {
                /* If next char is not backslash copy it and continue */
                if (*data != '\\') {
                        *buf++ = *data++;
                        continue;
                }
                /* If we have anything else then x or X after, return error. */
                if (data[1] != 'x' && data[1] != 'X')
                        return -1;
                val = (hexval(data[2]) << 4) | hexval(data[3]);
                /* If not valid hex, return error. */
                if (val & ~0xff)
                        return -1;
                *buf++ = val;
                data += 4;
                /* Keep track of converted numbers, "for fun". */
                ++converted; 
        }
        len = buf - *buf_ptr;

        fprintf(stderr, "%d hex values converted.\n", converted);

        return len;
}

int main(int argc, char *argv[])
{
        int len;
        unsigned char *buf = NULL;
        if (argc < 2) {
                fprintf(stderr, "Missing argument.\n");
                return 1;
        }

        if ((len = str2bin(argv[1], &buf)) < 0) {
                fprintf(stderr, "Bad input.\n");
                return 2;
        }

        xxd(buf, len);

        free(buf);

    return 0;
}

给你这样的东西:

$ ./hexin "Hello\x20\x44\x65\x08\x01\x00\x00\xf7\xdf\x00\x02Bye"
11 hex values converted.
000: 48 65 6c 6c 6f 20 44 65 08 01 00 00 f7 df 00 02   Hello De........
010: 42 79 65                                          Bye

答案 1 :(得分:1)

\x表示法仅适用于代码本身的字符串文字,而不适用于用户输入的内容。如果你想要字符\ x04,那么直接在字符串中键入♦。