将不可打印的ASCII字符转换为二进制

 晴子suerw_980 发布于 2023-02-04 15:12

我试图将一个不可打印的ASCII字符串转换为二进制.这是代码:

int main(int argc, char *argv[])
{
    char str[32];
    sprintf(str,"\x01\x00\x02");

    printf("\n[%x][%x][%x]",str[0],str[1],str[2]);
    return 1;
}

我希望输出应该是[1] [0] [2],但它打印[1] [0] [4].

我在这做错了什么?

2 个回答
  • sprintf操作在一审结束了\x00在你的字符串字面量,因为NUL(U + 0000)终止字符串在C(当你写的编译器不会抱怨\x00一个字符串内,可以说是语言的不良特性).因此str[2]访问未初始化的内存和程序有权打印完全废话甚至崩溃.

    要做你想做的事,只需消除sprintf:

    int main(void)
    {
        static const unsigned char str[32] = 
        { 0x01, 0x00, 0x02 };  // will be zero-filled to declared size
    
        printf("[%02x][%02x][%02x]\n", str[0], str[1], str[2]);
    
        return 0;
    }
    

    (二进制数据应始终存储在unsigned char 数组中,而不是普通char;或者uint8_t如果你有.因为U + 0000终止字符串,我认为使用数组文字而不是字符串文字来编写嵌入式二进制数据是更好的方式;但它更多的static const是打字.这只是因为数据永远不会被修改并且在编译时就已知;程序在没有它的情况下就可以工作.不要声明argc,argv如果你不打算使用它们.返回零,而不是一个,来自main表示成功完成.)

    (sprintf由于其他原因,使用你使用它的方式是一个坏主意:例如,如果你的二进制块包含\x25(也称为%ASCII),它将尝试读取待格式化的其他参数,并再次打印完成无意义或崩溃.如果你有充分的理由不仅仅使用静态初始化数据,那么复制二进制数据块的正确方法是memcpy.)

    2023-02-04 15:14 回答
  • C字符串以空字节结尾,因此sprintf只读取直到\x00.相反,您可以使用memcpy(像这样)或简单地初始化

    char str[32] = "\x01\x00\x02";
    

    2023-02-04 15:14 回答
撰写答案
今天,你开发时遇到什么问题呢?
立即提问
热门标签
PHP1.CN | 中国最专业的PHP中文社区 | PNG素材下载 | DevBox开发工具箱 | json解析格式化 |PHP资讯 | PHP教程 | 数据库技术 | 服务器技术 | 前端开发技术 | PHP框架 | 开发工具 | 在线工具
Copyright © 1998 - 2020 PHP1.CN. All Rights Reserved 京公网安备 11010802041100号 | 京ICP备19059560号-4 | PHP1.CN 第一PHP社区 版权所有