C 无法将十六进制字节正确打包到无符号字符数组或指针中

C 无法将十六进制字节正确打包到无符号字符数组或指针中,c,struct,hex,C,Struct,Hex,我试图用无符号字符数组或指针模拟结构,但无法获得相同的十六进制值 .print()的输入正确。 我试图从stringBytes_Data或Data_hexStrFormatted with print()获得相同的效果 有人能提供建议吗 给定 和查看数据的功能: static void print(char *intro_message, unsigned char *text_addr, unsigned int size) { unsigned int

我试图用无符号字符数组或指针模拟结构,但无法获得相同的十六进制值

.print()的输入正确。 我试图从stringBytes_Data或Data_hexStrFormatted with print()获得相同的效果

有人能提供建议吗

给定

和查看数据的功能:

static void print(char *intro_message, unsigned char *text_addr,
                    unsigned int size) {
unsigned int   i;

for (i = 0;  i < size;  i++) {
    printf("%2x ", text_addr[i]);
    if ((i & 0xf) == 0xf)
        printf("\n");
}
printf("\n");
}
我试过了,但结果是错的:

unsigned char* data_hexStrFormatted;

int lengthOfStr = strlen(stringBytes_Data);
int charCounterForNewStr = 0;       
int formattedLength = (2*lengthOfStr)+1;

data_hexStrFormatted = (unsigned char*) malloc((formattedLength)*sizeof(unsigned char)); // x2 as we add \x to XX, and 1 for NULL end char


for(i=0; i<lengthOfStr; i=i+2) { 
      // prepend \x
         data_hexStrFormatted[charCounterForNewStr++] = '\\';
         data_hexStrFormatted[charCounterForNewStr++] = 'x';

      data_hexStrFormatted[charCounterForNewStr++] = stringBytes_Data[i]; 
      data_hexStrFormatted[charCounterForNewStr++] = stringBytes_Data[i+1];
} 
data_hexStrFormatted[formattedLength-1] = '\0';

printf("%s\n", data_hexStrFormatted);
printf("%d byte length \n", strlen(data_hexStrFormatted)/4);

 print("data_hexStrFormatted",
                    (unsigned char *)
                    data_hexStrFormatted,
                    (formattedLength)/4); 
unsigned char*data\u hexStrFormatted;
int lengthOfStr=strlen(stringBytes_数据);
int charCounterForNewStr=0;
int formattedLength=(2*lengthOfStr)+1;
数据_hexStrFormatted=(无符号字符*)malloc((格式化长度)*sizeof(无符号字符));//当我们将\x添加到XX时为x2,空结束字符为1
对于(i=0;i你似乎在问:

  • 给定一个包含成对十六进制数字的字符串,是否将十六进制数字转换为字节值
如果是,则可以使用类似于以下的代码:

static inline int hexit(const unsigned char c)
{
    static const char hex_digits[] = "0123456789ABCDEF";
    return strchr(hex_digits, toupper(c)) - hex_digits;
}
此函数适用于有效的十六进制数字;对于无效的输入,它将产生无意义的结果。如果您决定需要检测错误的输入,则需要对其进行改进。还有其他方法可以编写此函数(事实上,它们很多)。一个有效的方法是使用正确的值静态初始化256字节的数组,因此只需编写
返回十六进制数组[c];

char* stringBytes_Data = "6bc1bee22e409f96e93d7e117393172aae2d8a571e03ac9c9eb76fac45af8e5130c81c46a35ce411e5fbc1191a0a52eff69f2445df4f9b17ad2b417be66c3710";

size_t len = strlen(stringBytes_Data);
char buffer[len / 2];

assert(len % 2 == 0);

for (size_t i = 0; i < len; i += 2)
    buffer[i / 2] = hexit(stringBytes_Data[i]) << 4 | hexit(stringBytes_Data[i+1]);

printf("%.*s\n", (int)len/2, buffer);
样本输出:

6b c1 be e2 2e 40 9f 96 e9 3d 7e 11 73 93 17 2a 
ae 2d 8a 57 1e  3 ac 9c 9e b7 6f ac 45 af 8e 51 
30 c8 1c 46 a3 5c e4 11 e5 fb c1 19 1a  a 52 ef 
f6 9f 24 45 df 4f 9b 17 ad 2b 41 7b e6 6c 37 10 

buffer:
6b c1 be e2 2e 40 9f 96 e9 3d 7e 11 73 93 17 2a 
ae 2d 8a 57 1e  3 ac 9c 9e b7 6f ac 45 af 8e 51 
30 c8 1c 46 a3 5c e4 11 e5 fb c1 19 1a  a 52 ef 
f6 9f 24 45 df 4f 9b 17 ad 2b 41 7b e6 6c 37 10 
工作代码-#1 重做-以前的版本有各种“关闭两倍”的错误,这些错误被系统调零缓冲区部分隐藏

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

struct Vector
{
    char *input;
    unsigned char len;
};

static struct Vector tv2 =
{
    .input = "\x6b\xc1\xbe\xe2\x2e\x40\x9f\x96"
             "\xe9\x3d\x7e\x11\x73\x93\x17\x2a"
             "\xae\x2d\x8a\x57\x1e\x03\xac\x9c"
             "\x9e\xb7\x6f\xac\x45\xaf\x8e\x51"
             "\x30\xc8\x1c\x46\xa3\x5c\xe4\x11"
             "\xe5\xfb\xc1\x19\x1a\x0a\x52\xef"
             "\xf6\x9f\x24\x45\xdf\x4f\x9b\x17"
             "\xad\x2b\x41\x7b\xe6\x6c\x37\x10",
    .len = 64,
};

static inline int hexit(const unsigned char c)
{
    static const char hex_digits[] = "0123456789ABCDEF";
    return strchr(hex_digits, toupper(c)) - hex_digits;
}

static void print(const char *tag, const unsigned char *data, size_t size)
{
    printf("%s:\n", tag);
    for (size_t i = 0; i < size; i++)
    {
        printf("%2x ", data[i]);
        if ((i & 0x0F) == 0x0F)
            printf("\n");
    }
    printf("\n");
}

static void print_text(const char *tag, const char *data, size_t datalen)
{
    char buffer[datalen / 2];

    assert(datalen % 2 == 0);

    for (size_t i = 0; i < datalen; i += 2)
        buffer[i / 2] = hexit(data[i]) << 4 | hexit(data[i + 1]);

    printf("%s: [[%.*s]]\n", tag, (int)datalen / 2, buffer);
    assert(memcmp(buffer, tv2.input, tv2.len) == 0);
    print(tag, (unsigned char *)buffer, datalen / 2);
}

int main(void)
{
    char *stringBytes_Data =
        "6bc1bee22e409f96e93d7e117393172a"
        "ae2d8a571e03ac9c9eb76fac45af8e51"
        "30c81c46a35ce411e5fbc1191a0a52ef"
        "f69f2445df4f9b17ad2b417be66c3710"
    ;

    print_text("buffer", stringBytes_Data, strlen(stringBytes_Data));
    return 0;
}
将原始输出转换为UTF-8,如同它是ISO 8859-15(或8859-1):


数据似乎没有任何特别的意义,但美在旁观者的眼中。

我可能无法在我的系统上使用assert()。如果这样做,则打印文本(“缓冲区”(unsigned char*)缓冲区,len);只有前32个字节是正确的。你很接近。非常接近。你能给出一个替代方案吗?如果打印显示相同的内容,应该解决它。
assert
不必存在;你可以忽略这种可能性,或者删除奇数字符,或者不做任何操作就返回,或者返回错误条件,或者任何可能的错误lse您可以选择处理错误。修复
hexit()
以报告错误的hex将更加烦躁;您必须更改其接口或使用方式。我删除了assert(),但给定输入,它没有显示完全正确的值。您是说“工作示例”部分中的代码行为不正常吗?对我来说,它似乎工作正常。我在
print_text()中添加了一个检查
验证
buffer
中转换的数据是否与
tv2
结构中的数据相同,并且确实相同。测试是:
assert(memcmp(buffer,tv2.input,tv2.len)==0);
之间的转换“\xAB”
和带有十六进制值的字符
AB
是您的编译器所做的事情-没有等效的运行时。正如回答者所建议的,您必须专门编写代码来进行转换。
#include <assert.h>
#include <ctype.h>
#include <stdio.h>
#include <string.h>

struct Vector
{
    char *input;
    unsigned char len;
};

static struct Vector tv2 =
{
    .input = "\x6b\xc1\xbe\xe2\x2e\x40\x9f\x96"
             "\xe9\x3d\x7e\x11\x73\x93\x17\x2a"
             "\xae\x2d\x8a\x57\x1e\x03\xac\x9c"
             "\x9e\xb7\x6f\xac\x45\xaf\x8e\x51"
             "\x30\xc8\x1c\x46\xa3\x5c\xe4\x11"
             "\xe5\xfb\xc1\x19\x1a\x0a\x52\xef"
             "\xf6\x9f\x24\x45\xdf\x4f\x9b\x17"
             "\xad\x2b\x41\x7b\xe6\x6c\x37\x10",
    .len = 64,
};

static inline int hexit(const unsigned char c)
{
    static const char hex_digits[] = "0123456789ABCDEF";
    return strchr(hex_digits, toupper(c)) - hex_digits;
}

static void print(unsigned char *text_addr, unsigned int size)
{
    unsigned int i;

    for (i = 0; i < size; i++)
    {
        printf("%2x ", text_addr[i]);
        if ((i & 0xf) == 0xf)
            printf("\n");
    }
    printf("\n");
}

static void print2(const char *tag, const unsigned char *data, size_t size)
{
    printf("%s:\n", tag);
    for (size_t i = 0; i < size; i++)
    {
        printf("%2x ", data[i]);
        if ((i & 0x0F) == 0x0F)
            printf("\n");
    }
    printf("\n");
}

static void print_text(const char *tag, const char *data, size_t datalen)
{
    char buffer[datalen / 2];

    assert(datalen % 2 == 0);

    for (size_t i = 0; i < datalen; i += 2)
        buffer[i / 2] = hexit(data[i]) << 4 | hexit(data[i + 1]);

    //printf("%s: [[%.*s]]\n", tag, (int)datalen / 2, buffer);
    assert(memcmp(buffer, tv2.input, tv2.len) == 0);
    print((unsigned char *)buffer, datalen / 2);
    print2(tag, (unsigned char *)buffer, datalen / 2);
}

int main(void)
{
    char *stringBytes_Data =
        "6bc1bee22e409f96e93d7e117393172a"
        "ae2d8a571e03ac9c9eb76fac45af8e51"
        "30c81c46a35ce411e5fbc1191a0a52ef"
        "f69f2445df4f9b17ad2b417be66c3710"
    ;

    print_text("buffer", stringBytes_Data, strlen(stringBytes_Data));
    return 0;
}
6b c1 be e2 2e 40 9f 96 e9 3d 7e 11 73 93 17 2a 
ae 2d 8a 57 1e  3 ac 9c 9e b7 6f ac 45 af 8e 51 
30 c8 1c 46 a3 5c e4 11 e5 fb c1 19 1a  a 52 ef 
f6 9f 24 45 df 4f 9b 17 ad 2b 41 7b e6 6c 37 10 

buffer:
6b c1 be e2 2e 40 9f 96 e9 3d 7e 11 73 93 17 2a 
ae 2d 8a 57 1e  3 ac 9c 9e b7 6f ac 45 af 8e 51 
30 c8 1c 46 a3 5c e4 11 e5 fb c1 19 1a  a 52 ef 
f6 9f 24 45 df 4f 9b 17 ad 2b 41 7b e6 6c 37 10 
#include <assert.h>
#include <ctype.h>
#include <stdio.h>
#include <string.h>

struct Vector
{
    char *input;
    unsigned char len;
};

static struct Vector tv2 =
{
    .input = "\x6b\xc1\xbe\xe2\x2e\x40\x9f\x96"
             "\xe9\x3d\x7e\x11\x73\x93\x17\x2a"
             "\xae\x2d\x8a\x57\x1e\x03\xac\x9c"
             "\x9e\xb7\x6f\xac\x45\xaf\x8e\x51"
             "\x30\xc8\x1c\x46\xa3\x5c\xe4\x11"
             "\xe5\xfb\xc1\x19\x1a\x0a\x52\xef"
             "\xf6\x9f\x24\x45\xdf\x4f\x9b\x17"
             "\xad\x2b\x41\x7b\xe6\x6c\x37\x10",
    .len = 64,
};

static inline int hexit(const unsigned char c)
{
    static const char hex_digits[] = "0123456789ABCDEF";
    return strchr(hex_digits, toupper(c)) - hex_digits;
}

static void print(const char *tag, const unsigned char *data, size_t size)
{
    printf("%s:\n", tag);
    for (size_t i = 0; i < size; i++)
    {
        printf("%2x ", data[i]);
        if ((i & 0x0F) == 0x0F)
            printf("\n");
    }
    printf("\n");
}

static void print_text(const char *tag, const char *data, size_t datalen)
{
    char buffer[datalen / 2];

    assert(datalen % 2 == 0);

    for (size_t i = 0; i < datalen; i += 2)
        buffer[i / 2] = hexit(data[i]) << 4 | hexit(data[i + 1]);

    printf("%s: [[%.*s]]\n", tag, (int)datalen / 2, buffer);
    assert(memcmp(buffer, tv2.input, tv2.len) == 0);
    print(tag, (unsigned char *)buffer, datalen / 2);
}

int main(void)
{
    char *stringBytes_Data =
        "6bc1bee22e409f96e93d7e117393172a"
        "ae2d8a571e03ac9c9eb76fac45af8e51"
        "30c81c46a35ce411e5fbc1191a0a52ef"
        "f69f2445df4f9b17ad2b417be66c3710"
    ;

    print_text("buffer", stringBytes_Data, strlen(stringBytes_Data));
    return 0;
}
buffer: [[k???.@???=~s?*?-?W????o?E??Q0?F?\????
R???$E?O??+A{?l7]]
buffer:
6b c1 be e2 2e 40 9f 96 e9 3d 7e 11 73 93 17 2a 
ae 2d 8a 57 1e  3 ac 9c 9e b7 6f ac 45 af 8e 51 
30 c8 1c 46 a3 5c e4 11 e5 fb c1 19 1a  a 52 ef 
f6 9f 24 45 df 4f 9b 17 ad 2b 41 7b e6 6c 37 10 
buffer: [[kÁŸâ.@é=~s*®-W¬·o¬E¯Q0ÈF£\äåûÁ
Rïö$EßO­+A{æl7]]
buffer:
6b c1 be e2 2e 40 9f 96 e9 3d 7e 11 73 93 17 2a 
ae 2d 8a 57 1e  3 ac 9c 9e b7 6f ac 45 af 8e 51 
30 c8 1c 46 a3 5c e4 11 e5 fb c1 19 1a  a 52 ef 
f6 9f 24 45 df 4f 9b 17 ad 2b 41 7b e6 6c 37 10