1

スタンドアロン asio を使用して、read_some でサーバーを実装しました。私のサーバーループは、ソケットから受信したすべてのデータを蓄積します。以下の簡素化されたコードは正しく動作しませんが、inbuf.prepare() ステートメントをループに移動することで修正できます。

asio::streambuf inbuf;
asio::streambuf::mutable_buffers_type inbufs = inbuf.prepare(4096);
while( connected )
{
    asio::error_code ec;
    size_t bytes_read = Socket().read_some(inbufs,ec);
    inbuf.commit(bytes_read);
    std::string s = std::string(asio::buffers_begin(inbufs),
            asio::buffers_begin(inbufs) + inbuf.size());
    inbuf.consume(bytes_read);
}

prepare() がループの外にあり、接続が確立されてから読み取られた合計バイト数が 4096 境界を超える場合、 string はその境界までのデータのみを保持します。つまり、s は bytes_read よりも短くなります。prepare() をループの外に置きたい場合は、次のような消費ループが必要になると推測しましたが、これもうまくいきませんでした。

asio::streambuf inbuf;
asio::streambuf::mutable_buffers_type inbufs = inbuf.prepare(4096);
while( connected )
{
    asio::error_code ec;
    size_t bytes_read = Socket().read_some(inbufs,ec);
    while(bytes_read > 0)
    {
        inbuf.commit(bytes_read);
        std::string s = std::string(asio::buffers_begin(inbufs),
            asio::buffers_begin(inbufs) + inbuf.size());
        inbuf.consume(inbuf.size());
        bytes_read -= s.size();
    }
}

prepare() の役割と、なぜ繰り返し呼び出す必要があるのか​​ を明確にすることはできますか?

4

2 に答える 2