C++ 通过Boost ASIO服务器发送缓冲区-发送错误数据

C++ 通过Boost ASIO服务器发送缓冲区-发送错误数据,c++,arrays,boost,server,boost-asio,C++,Arrays,Boost,Server,Boost Asio,谁能告诉我如何将存储在数组中的十六进制值不变地发送到客户端 每当我通过boost服务器向客户机发送一个十六进制字符数组时,它就会将其转换为ASCII/垃圾(无法确定它是什么) 对于Ex: 我正试图发送 "24 bb ff 0f 02 08 01 e0 01 e0 02 08 0f 2d 0f 00 23 61" 通过Boost asio服务器在字符阵列中 编辑: 客户正在接收 "32 34 62 62 66 66 30 66 30 32 30 38 30 31 65 30 30 31 65 3

谁能告诉我如何将存储在数组中的十六进制值不变地发送到客户端

每当我通过boost服务器向客户机发送一个十六进制字符数组时,它就会将其转换为ASCII/垃圾(无法确定它是什么)

对于Ex:

我正试图发送

"24 bb ff 0f 02 08 01 e0 01 e0 02 08 0f 2d 0f 00 23 61"
通过Boost asio服务器在字符阵列中

编辑:

客户正在接收

"32 34 62 62 66 66 30 66 30 32 30 38 30 31 65 30 30 31 65 30 30 32 30 38 30 66 32 64 30 66 30 30 32 33 36 31"
这是我正在使用的一段代码

char Sendingdata_[512];
string finalHex = "24bbff0f020801e001e002080f2d0f002361";
strcpy(Sendingdata_, finalHex.c_str());
boost::asio::async_write(socket_, boost::asio::buffer(Sendingdata_,bytes_transferred), boost::bind(&session::handle_write, this, boost::asio::placeholders::error));

我应该使用不同的缓冲区还是任何其他方式来发送十六进制值?

因为您发送的是一个众所周知的内存垃圾模式(),我假设您读取的内容超过了缓冲区的结尾,或者您正在取消引用一个过时的指针

我看到人们在使用ASIO时犯的一个常见错误是:

void foo() {
     std::string packet = "hello world";

     boost::asio::async_write(socket_, asio::buffer(packet), my_callback);
}
问题是使用带有异步调用的stacklocal缓冲区
async\u write
将立即返回,
foo
将返回<代码>数据包可能在异步操作访问它之前就消失了


如果您正在运行调试堆库,这是导致您读取垃圾桶模式而不是缓冲区内容的原因之一。

如果代码试图发送37个字节以上的数据,那么它将发送未初始化的内存。如果它试图发送超过512字节的数据,那么它读取的数据超出了缓冲区的末尾。在任何一种情况下,都可能发送内存垃圾模式

发送数据
缓冲区为512字节,但其中只有37个字节已初始化

字符发送数据u512];//512个单位化值。
std::string finalHex=字符串文字;//36个ASCII字符+空终止符。
strcpy(发送数据,finalHex.c_str());//复制37个字符
boost::asio::async_write(…,boost::asio::buffer(发送数据,传输字节),…);

正在为
finalHex
字符串提供字符串文本。例如,为字符串指定
“2400bb”
,将存储
'2'
'4'
'0'
'0'
'b'
'b'
ASCII字符

std::string ascii=“2400bb”;
断言(ascii.length()==6);
断言('2'==ascii[0]);
断言('4'==ascii[1]);
断言('0'==ascii[2]);
断言('0'==ascii[3]);
断言('b'==ascii[4]);
断言('b'==ascii[5]);
考虑使用向量,以十六进制表示法提供数值:

std::vector hex={0x24,0x00,0xbb};
断言(十六进制大小()==3);
断言(0x24==hex[0]);
断言(0x00==hex[1]);
断言(0xbb==hex[2]);
或者,可以通过提供
\x
控制字符来使用
std::string
,以指示后续值为十六进制。但是,在解释值时可能需要执行显式强制转换,并使用处理字符串中空字符的构造函数:

std::字符串十六进制(“\x24\x00\xbb”,3);
//或者:std::string十六进制{0x24,0x00,static_cast(0xbb)};
断言(十六进制大小()==3);
断言(0x24==static_cast(十六进制[0]);
断言(0x00==static_cast(十六进制[1]);
断言(0xbb==static_cast(十六进制[2]);

以下是差异和Asio缓冲区使用的示例:

#包括
#包括
#包括
#包括
#包括
#包括
int main()
{
//字符串文字。
std::string ascii=“2400bb”;
断言(ascii.length()==6);
断言('2'==ascii[0]);
断言('4'==ascii[1]);
断言('0'==ascii[2]);
断言('0'==ascii[3]);
断言('b'==ascii[4]);
断言('b'==ascii[5]);
//验证asio缓冲区。
自动ascii_buffer=boost::asio::buffer(ascii);
断言(ascii.length()==boost::asio::buffer_size(ascii_buffer));
断言(std::equal)(
boost::asio::buffers\u begin(ascii\u buffer),
boost::asio::buffers\u end(ascii\u buffer),
std::begin(ascii));
//十六进制值。
向量十六进制={0x24,0x00,0xbb};
//或者:无符号字符十六进制[]={0x24,0x00,0xbb};
断言(十六进制大小()==3);
断言(0x24==hex[0]);
断言(0x00==hex[1]);
断言(0xbb==hex[2]);
//验证asio缓冲区。
自动十六进制缓冲=boost::asio::buffer(十六进制);
断言(hex.size()==boost::asio::buffer_size(hex_buffer));
断言(std::equal)(
boost::asio::buffers\u begin(十六进制缓冲区),
boost::asio::buffers\u end(十六进制缓冲区),
标准::开始(十六进制),
标准::等于();
//带十六进制的字符串。由于0x00在字符串中,字符串(char*)构造函数
//不能使用。
std::字符串hex2(“\x24\x00\xbb”,3);
//或者:std::string hex2{0x24,0x00,static_cast(0xbb)};
断言(hex2.size()=3);
断言(0x24==static_cast(hex2[0]);
断言(0x00==static_cast(hex2[1]);
断言(0xbb==static_cast(hex2[2]);
}

请阅读并显示用于发送的源代码。修复尾数后,您将收到“BAADF00D BAADF00D BAADF00D…”,因此两端都有一个bug,但无法猜测其位置。请注意,没有“十六进制值”这类东西-值有十六进制表示,但是数字10是相同的,不管你是写
10
0xa
,还是
012
。字符串
“10”
表示数组
{49,48,0}
。您应该包含代码。我们不是通灵者。谢谢@sehe,是的,它是通过缓冲区的末尾发送的,在客户端接收到数组中每个字符的ASCII之后,比如“32 34 62 62 66 66 30 66 30 30 32 30 38 31 65 30 30 30 30 32 30 38 66 32 64 30 66 30 30 32 33 36 31”,那么我应该如何发送十六进制值而不转换为ASCII,我不在这里做任何转换。我应该使用不同的缓冲区/任何数据结构吗???谢谢@Tanner Sansbury,我找到了一些关于使用字符串的文章,正如您所解释和实现的,非常感谢您提供了非常有用的信息。现在我正在发送“\x24\xbb\xff\x0f\x02\x08\x01\xe0\x01\xe0\x02\x08\x0f\x2d\x0f\x00\x23\x61”,客户端只能接收“\x24\xbb\xff\x0f\x02\x”