SHOW:
|
|
- or go back to the newest paste.
1 | class Protocol::AsyncHelper { | |
2 | typedef boost::shared_ptr<Protocol::AsyncHelper> AsyncHelperP; | |
3 | public: | |
4 | AsyncHelper(Protocol &protocol) : | |
5 | buf(), | |
6 | protocol_(protocol) {} | |
7 | template <class AsyncReadStream> | |
8 | void AsyncReadMessage(AsyncReadStream &stream, | |
9 | AsyncReadHandler handler) { | |
10 | AsyncHelperP ptr(this); | |
11 | buf.reset(new uint8_t[sizeof(uint32_t) * 2]); | |
12 | boost::asio::async_read(stream, boost::asio::buffer(&buf[0], | |
13 | sizeof(uint32_t) * 2), | |
14 | boost::bind(&AsyncHelper | |
15 | ::AsyncReadHeader<AsyncReadStream>, | |
16 | this, | |
17 | boost::asio::placeholders::error, | |
18 | boost::ref(stream), | |
19 | handler, | |
20 | ptr)); | |
21 | } | |
22 | private: | |
23 | template <class AsyncReadStream> | |
24 | void AsyncReadHeader(const boost::system::error_code &ec, | |
25 | AsyncReadStream &stream, | |
26 | AsyncReadHandler handler, | |
27 | AsyncHelperP ptr) { | |
28 | if (ec) { | |
29 | handler(MessageP(), ProtocolExceptionP( | |
30 | new ProtocolException("IO error in Protocol::" | |
31 | "AsyncHelper::AsyncReadHeader."))); | |
32 | } else { | |
33 | uint32_t id = reinterpret_cast<uint32_t*>(&buf[0])[0]; | |
34 | uint32_t size = reinterpret_cast<uint32_t*>(&buf[0])[1]; | |
35 | buf.reset(new uint8_t[size]); | |
36 | boost::asio::async_read(stream, boost::asio::buffer(&buf[0], size), | |
37 | boost::bind(&AsyncHelper | |
38 | ::AsyncReadBody<AsyncReadStream>, | |
39 | this, | |
40 | boost::asio::placeholders::error, | |
41 | id, | |
42 | size, | |
43 | handler, | |
44 | ptr)); | |
45 | } | |
46 | } | |
47 | ||
48 | template <class AsyncReadStream> | |
49 | void AsyncReadBody(const boost::system::error_code &ec, | |
50 | uint32_t id, uint32_t size, | |
51 | AsyncReadHandler handler, | |
52 | AsyncHelperP ptr) { | |
53 | if (ec) { | |
54 | handler(MessageP(), ProtocolExceptionP( | |
55 | new ProtocolException("IO error in Protocol::" | |
56 | "AsyncHelper::AsyncReadBody."))); | |
57 | } else { | |
58 | ProtocolExceptionP exception; | |
59 | MessageP message; | |
60 | try { | |
61 | message = protocol_.helpers_[id]->ReadMessage(&buf[0], size); | |
62 | } catch (ProtocolException &e) { | |
63 | exception.reset(new ProtocolException(e)); | |
64 | } | |
65 | handler(message, exception); | |
66 | } | |
67 | } | |
68 | private: | |
69 | boost::scoped_array<uint8_t> buf; | |
70 | Protocol &protocol_; | |
71 | }; | |
72 | ||
73 | template <class AsyncReadStream> | |
74 | - | // memleak here if io_service is turning off. |
74 | + | |
75 | AsyncReadHandler handler) { | |
76 | (new AsyncHelper(*this))->AsyncReadMessage(stream, handler); | |
77 | } |