WebSocket optimizations (API Change):

The websocket stream is optimized to contain a small
circular static buffer, reducing the number of I/O calls when
reading data. The size of the buffer is tuned for maximum
performance with TCP/IP and no long needs configuration:

* read_some replaces read_frame
* write_some replaces write_Frame
* async_read_some replaces async_read_frame
* async_write_some replaces async_write_frame

* websocket::stream::read_buffer_size is removed

Actions Required:

* Remove calls websocket::stream::read_buffer_size

* Use read_some and write_some instead of read_frame and write_frame
This commit is contained in:
Vinnie Falco
2017-07-20 08:15:32 -07:00
parent 28b5275c73
commit cb501a07c8
21 changed files with 2350 additions and 1241 deletions
+3 -3
View File
@@ -163,7 +163,7 @@ boost::asio::ip::tcp::socket sock{ios};
//[ws_snippet_16
multi_buffer buffer;
for(;;)
if(ws.read_frame(buffer))
if(ws.read_some(buffer, 0))
break;
ws.binary(ws.got_binary());
consuming_buffers<multi_buffer::const_buffers_type> cb{buffer.data()};
@@ -172,12 +172,12 @@ boost::asio::ip::tcp::socket sock{ios};
using boost::asio::buffer_size;
if(buffer_size(cb) > 512)
{
ws.write_frame(false, buffer_prefix(512, cb));
ws.write_some(false, buffer_prefix(512, cb));
cb.consume(512);
}
else
{
ws.write_frame(true, cb);
ws.write_some(true, cb);
break;
}
}
+1
View File
@@ -37,6 +37,7 @@ public:
check("beast.websocket", error::closed);
check("beast.websocket", error::failed);
check("beast.websocket", error::handshake_failed);
check("beast.websocket", error::buffer_overflow);
}
};
+16 -17
View File
@@ -264,7 +264,7 @@ public:
read(stream<NextLayer>& ws,
DynamicBuffer& buffer) const
{
ws.read(buffer);
return ws.read(buffer);
}
template<
@@ -279,10 +279,10 @@ public:
template<
class NextLayer, class ConstBufferSequence>
void
write_frame(stream<NextLayer>& ws, bool fin,
write_some(stream<NextLayer>& ws, bool fin,
ConstBufferSequence const& buffers) const
{
ws.write_frame(fin, buffers);
ws.write_some(fin, buffers);
}
template<
@@ -521,11 +521,11 @@ public:
template<
class NextLayer, class ConstBufferSequence>
void
write_frame(stream<NextLayer>& ws, bool fin,
write_some(stream<NextLayer>& ws, bool fin,
ConstBufferSequence const& buffers) const
{
error_code ec;
ws.async_write_frame(fin, buffers, yield_[ec]);
ws.async_write_some(fin, buffers, yield_[ec]);
if(ec)
throw system_error{ec};
}
@@ -551,7 +551,6 @@ public:
ws.auto_fragment(true);
ws.write_buffer_size(2048);
ws.binary(false);
ws.read_buffer_size(8192);
ws.read_message_max(1 * 1024 * 1024);
try
{
@@ -592,7 +591,7 @@ public:
{
static std::size_t constexpr limit = 200;
std::size_t n;
for(n = 0; n < limit; ++n)
for(n = 0; n <= limit; ++n)
{
test::fail_counter fc{n};
try
@@ -904,7 +903,7 @@ public:
{
static std::size_t constexpr limit = 200;
std::size_t n;
for(n = 199; n < limit; ++n)
for(n = 0; n < limit; ++n)
{
test::fail_counter fc{n};
try
@@ -1539,8 +1538,8 @@ public:
ws.handshake("localhost", "/", ec);
if(! BEAST_EXPECTS(! ec, ec.message()))
return;
ws.write_frame(false, sbuf("u"));
ws.write_frame(true, sbuf("v"));
ws.write_some(false, sbuf("u"));
ws.write_some(true, sbuf("v"));
multi_buffer b;
ws.read(b, ec);
if(! BEAST_EXPECTS(! ec, ec.message()))
@@ -1562,7 +1561,7 @@ public:
ws.handshake("localhost", "/", ec);
if(! BEAST_EXPECTS(! ec, ec.message()))
break;
ws.async_write_frame(false,
ws.async_write_some(false,
boost::asio::null_buffers{},
[&](error_code)
{
@@ -1573,7 +1572,7 @@ public:
break;
//
// Destruction of the io_service will cause destruction
// of the write_frame_op without invoking the final handler.
// of the write_some_op without invoking the final handler.
//
break;
}
@@ -1687,9 +1686,9 @@ public:
BEAST_EXPECT(s == "payload");
});
ws.ping("payload");
c.write_frame(ws, false, sbuf("Hello, "));
c.write_frame(ws, false, sbuf(""));
c.write_frame(ws, true, sbuf("World!"));
c.write_some(ws, false, sbuf("Hello, "));
c.write_some(ws, false, sbuf(""));
c.write_some(ws, true, sbuf("World!"));
{
// receive echoed message
multi_buffer db;
@@ -1783,13 +1782,13 @@ public:
if(! pmd.client_enable)
{
// expected cont
c.write_frame(ws, false, boost::asio::null_buffers{});
c.write_some(ws, false, boost::asio::null_buffers{});
c.write_raw(ws,
cbuf(0x81, 0x80, 0xff, 0xff, 0xff, 0xff));
restart(error::closed);
// message size above 2^64
c.write_frame(ws, false, cbuf(0x00));
c.write_some(ws, false, cbuf(0x00));
c.write_raw(ws,
cbuf(0x80, 0xff, 0xff, 0xff, 0xff, 0xff,
0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff, 0xff));
@@ -10,6 +10,7 @@
#include <beast/core/multi_buffer.hpp>
#include <beast/websocket/stream.hpp>
#include <boost/asio.hpp>
#include <boost/lexical_cast.hpp>
#include <boost/optional.hpp>
#include <atomic>
+1 -1
View File
@@ -167,7 +167,7 @@ private:
{
std::geometric_distribution<std::size_t> dist{
double(4) / boost::asio::buffer_size(tb_)};
ws_.async_write_frame(true,
ws_.async_write_some(true,
beast::buffer_prefix(dist(rng_), tb_),
alloc_.wrap(std::bind(
&connection::on_write,