【问题标题】:Writing \x00 into a file将 \x00 写入文件
【发布时间】:2018-07-22 21:48:19
【问题描述】:

我必须向 USB 设备发送十六进制命令。

命令是:

echo -en "\x1b\x70\x00\x19\xfa" > /dev/usb/lp0

如果我在终端上写它,它就可以工作。但是,在 C++ 中,十六进制命令存在问题。 \x00 被检测为以 null 结尾的字符串。

我尝试了两种方法:

std::string cmd = "echo '\\x1b\\x70\\x00\\x19\\xfa' > /dev/usb/lp0";
std::system(cmd.c_str());

什么都没有发生。

还有:

std::ofstream device;
device.open("/dev/usb/lp0");
device << "\x1b\x70\x00\x19\xfa";
device.close();

设备什么都不做。

如何解决这个问题并使用\x00 字符串?

【问题讨论】:

  • 别忘了你需要在字符串文字中转义反斜杠。

标签: c++ hex


【解决方案1】:

使用write函数写入固定长度的字节。

由于您正在写入二进制数据,我建议您也以二进制模式打开文件,并写入实际的整数值而不是字符串。


示例代码

std::ofstream device ("/dev/usb/lp0",std::ofstream::binary);
std::uint8_t const message[] = { 0x1b, 0x70, 0x00, 0x19, 0xfa };
if (device)
    device.write(reinterpret_cast<char const*>(message), sizeof message);

【讨论】:

  • 感谢您的回答。你能举个例子吗?所以 std::ofstream 设备 ("/dev/usb/lp0",std::ofstream::binary) 以二进制形式写入。写函数会怎么样?
  • @grouser 添加了示例。
  • 它给出了从‘uint8_t* {aka unsigned char*}’到‘const char*’的错误无效转换
  • 如果你打算这样做,我建议在 device 实例化之后立即添加 device.rdbuf()-&gt;pubsetbuf(0, 0);,这样你就不会受到流缓冲区的干扰。
  • 这成功了!非常感谢@Someprogrammerdude 和 zwol
【解决方案2】:

我建议使用 unsigned char 的数组,而不是 C 字符串或 std::string 来存储命令:

const unsigned char usb_cmd[] = { 0x1b, 0x70, 0x00, 0x19, 0xfa };

这样对读者来说很明显这是一个二进制协议中的消息,而不是文本,也不是一个以 nul 结尾的字符串。此外,以这种方式声明,sizeof(usb_cmd) 将是要写入的正确字节数,而不是更多,sizeof(char*) 也不是。如果您需要在运行时更改命令的内容,请改用vector&lt;unsigned char&gt;

我还会使用操作系统原语对设备进行实际写入:

int fd = open("/dev/usb/lp0", O_RDWR);
if (fd == -1) {
    perror("/dev/usb/lp0");
    return -1;
}
ssize_t nwritten = write(fd, usb_cmd, sizeof usb_cmd);
if ((size_t)nwritten != sizeof usb_cmd) {
    if (nwritten < 0) {
        perror("/dev/usb/lp0: write error");
    } else {
        fprintf(stderr, "/dev/usb/lp0: short write (%zu of %zu bytes)\n",
                (size_t)nwritten, sizeof usb_cmd);
    }
    close(fd);
    return -1;
}
close(fd);
return 0;

这样,您可以确保一次写入的字节数完全正确;没有编码或缓冲层可以干扰。

【讨论】:

    猜你喜欢
    • 2014-02-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-01-16
    • 2016-04-13
    • 2011-01-28
    • 2015-01-19
    相关资源
    最近更新 更多