X-Git-Url: http://xvm.mit.edu/gitweb/invirt/third/libt4.git/blobdiff_plain/eb3d5c6416c0f0d1cad35e52af3231de7866fea8..26ade07ab0e62b98b452fbbd18edba0450035e35:/rpc/marshall.h?ds=sidebyside diff --git a/rpc/marshall.h b/rpc/marshall.h index 7b716e2..8592e4b 100644 --- a/rpc/marshall.h +++ b/rpc/marshall.h @@ -10,8 +10,8 @@ class marshall { private: - string buf_ = string(rpc_protocol::DEFAULT_RPC_SZ, 0); // Raw bytes buffer - size_t index_ = rpc_protocol::RPC_HEADER_SZ; // Read/write head position + string buf_ = string(rpc_protocol::DEFAULT_RPC_SZ, 0); + size_t index_ = rpc_protocol::RPC_HEADER_SZ; public: template @@ -19,10 +19,10 @@ class marshall { (void)pass{(*this << args)...}; } - void rawbytes(const void *p, size_t n) { + void write(const void *p, size_t n) { if (index_+n > buf_.size()) buf_.resize(index_+n); - copy((char *)p, (char *)p+n, &buf_[index_]); + std::copy((char *)p, (char *)p+n, &buf_[index_]); index_ += n; } @@ -35,7 +35,7 @@ class marshall { // delay looking up operator<<(marshall &, rpc_sz_t) until we define it // (i.e. we define an operator for marshalling uint32_t) template inline void - pack_header(const T & h) { + write_header(const T & h) { VERIFY(sizeof(T)+sizeof(S) <= rpc_protocol::RPC_HEADER_SZ); size_t saved_sz = index_; index_ = 0; @@ -47,32 +47,33 @@ class marshall { class unmarshall { private: string buf_; - size_t index_ = 0; + size_t index_ = rpc_protocol::RPC_HEADER_SZ; bool ok_ = false; public: template unmarshall(const string & s, bool has_header, Args && ... args) - : buf_(s),index_(rpc_protocol::RPC_HEADER_SZ) { + : buf_(s) { if (!has_header) buf_.insert(0, rpc_protocol::RPC_HEADER_SZ, 0); ok_ = (buf_.size() >= rpc_protocol::RPC_HEADER_SZ); (void)pass{(*this >> args)...}; } - bool ok() const { return ok_; } - bool okdone() const { return ok_ && index_ == buf_.size(); } + inline bool ok() const { return ok_; } + inline bool okdone() const { return ok_ && index_ == buf_.size(); } - void rawbytes(void * t, size_t n) { + void read(void * t, size_t n) { if (index_+n > buf_.size()) ok_ = false; - VERIFY(ok_); - copy(&buf_[index_], &buf_[index_+n], (char *)t); - index_ += n; + if (ok_) { + std::copy(&buf_[index_], &buf_[index_+n], (char *)t); + index_ += n; + } } template inline void - unpack_header(T & h) { + read_header(T & h) { VERIFY(sizeof(T)+sizeof(rpc_protocol::rpc_sz_t) <= rpc_protocol::RPC_HEADER_SZ); // first 4 bytes hold length field index_ = sizeof(rpc_protocol::rpc_sz_t); @@ -88,8 +89,8 @@ class unmarshall { // #define MARSHALL_RAW_NETWORK_ORDER_AS(_c_, _d_) \ -inline marshall & operator<<(marshall & m, _c_ x) { _d_ y = hton((_d_)x); m.rawbytes(&y, sizeof(_d_)); return m; } \ -inline unmarshall & operator>>(unmarshall & u, _c_ & x) { _d_ y; u.rawbytes(&y, sizeof(_d_)); x = (_c_)ntoh(y); return u; } +inline marshall & operator<<(marshall & m, _c_ x) { _d_ y = hton((_d_)x); m.write(&y, sizeof(_d_)); return m; } \ +inline unmarshall & operator>>(unmarshall & u, _c_ & x) { _d_ y; u.read(&y, sizeof(_d_)); x = (_c_)ntoh(y); return u; } #define MARSHALL_RAW_NETWORK_ORDER(_c_) MARSHALL_RAW_NETWORK_ORDER_AS(_c_, _c_) @@ -125,10 +126,9 @@ tuple_marshall_imp(marshall & m, tuple & t, tuple_indices) return m; } -template marshall & +template inline marshall & operator<<(marshall & m, tuple && t) { - using Indices = typename make_tuple_indices::type; - return tuple_marshall_imp(m, t, Indices()); + return tuple_marshall_imp(m, t, TUPLE_INDICES(Args)); } template inline unmarshall & @@ -137,10 +137,9 @@ tuple_unmarshall_imp(unmarshall & u, tuple t, tuple_indices unmarshall & +template inline unmarshall & operator>>(unmarshall & u, tuple && t) { - using Indices = typename make_tuple_indices::type; - return tuple_unmarshall_imp(u, t, Indices()); + return tuple_unmarshall_imp(u, t, TUPLE_INDICES(Args)); } // @@ -148,13 +147,13 @@ operator>>(unmarshall & u, tuple && t) { // // Implements struct marshalling via tuple marshalling of members. -#define MARSHALLABLE_STRUCT(_c_) \ -inline unmarshall & operator>>(unmarshall & u, _c_ & a) { return u >> a._tuple_(); } \ -inline marshall & operator<<(marshall & m, const _c_ a) { return m << a._tuple_(); } +template inline typename +enable_if::value, unmarshall>::type & +operator>>(unmarshall & u, T & a) { return u >> a._tuple_(); } -// our first two marshallable structs... -MARSHALLABLE_STRUCT(rpc_protocol::request_header) -MARSHALLABLE_STRUCT(rpc_protocol::reply_header) +template inline typename +enable_if::value, marshall>::type & +operator<<(marshall & m, const T a) { return m << a._tuple_(); } // // Marshalling for STL containers @@ -164,7 +163,7 @@ MARSHALLABLE_STRUCT(rpc_protocol::reply_header) template inline typename enable_if::value, marshall>::type & operator<<(marshall & m, const A & x) { - m << (unsigned int)x.size(); + m << (uint32_t)x.size(); for (const auto & a : x) m << a; return m; @@ -174,7 +173,7 @@ operator<<(marshall & m, const A & x) { template inline typename enable_if::value, unmarshall>::type & operator>>(unmarshall & u, A & x) { - unsigned n = u._grab(); + uint32_t n = u._grab(); x.clear(); while (n--) x.emplace_back(u._grab()); @@ -195,7 +194,7 @@ operator>>(unmarshall & u, pair & d) { // std::map template inline unmarshall & operator>>(unmarshall & u, map & x) { - unsigned n = u._grab(); + uint32_t n = u._grab(); x.clear(); while (n--) x.emplace(u._grab>()); @@ -205,7 +204,7 @@ operator>>(unmarshall & u, map & x) { // std::string inline marshall & operator<<(marshall & m, const string & s) { m << (uint32_t)s.size(); - m.rawbytes(s.data(), s.size()); + m.write(s.data(), s.size()); return m; } @@ -213,7 +212,7 @@ inline unmarshall & operator>>(unmarshall & u, string & s) { uint32_t sz = u._grab(); if (u.ok()) { s.resize(sz); - u.rawbytes(&s[0], sz); + u.read(&s[0], sz); } return u; }