Update Thrift CPP libraries to work with new generated source, change underlying buffers to use uint8_t* instead of std::string

Summary: Major overhaul to the CPP libraries.

Reviewed By: aditya

Test Plan: Again, keep an eye out for the unit tests commit

Notes: Initial perf tests show that Thrift is not only more robust than Pillar, but its implementation is actually around 10-20% faster. We can do about 10 RPC function calls with small data payloads in under 2ms. THAT IS FAST. THAT IS THRIFTY.




git-svn-id: https://svn.apache.org/repos/asf/incubator/thrift/trunk@664714 13f79535-47bb-0310-9956-ffa450edef68
diff --git a/lib/cpp/protocol/TBinaryProtocol.cc b/lib/cpp/protocol/TBinaryProtocol.cc
index 4c10bab..1f31c8d 100644
--- a/lib/cpp/protocol/TBinaryProtocol.cc
+++ b/lib/cpp/protocol/TBinaryProtocol.cc
@@ -1,140 +1,246 @@
 #include "protocol/TBinaryProtocol.h"
-using namespace std;
+using std::string;
 
-string TBinaryProtocol::readFunction(TBuf& buf) const {
-  // Let readString increment the buffer position
-  return readString(buf);
+uint32_t TBinaryProtocol::writeStructBegin(TTransport* out,
+                                           const string& name) const {
+  return 0;
 }
 
-string TBinaryProtocol::writeFunction(const string& name,
-                                      const string& args) const{
-  return writeString(name) + args;
+uint32_t TBinaryProtocol::writeStructEnd(TTransport* out) const {
+  return 0;
 }
 
-map<uint32_t, TBuf> TBinaryProtocol::readStruct(TBuf& buf) const {
-  map<uint32_t, TBuf> fieldMap;
+uint32_t TBinaryProtocol::writeFieldBegin(TTransport* out,
+                                          const string& name,
+                                          const TType fieldType,
+                                          const uint16_t fieldId) const {
+  return
+    writeByte(out, (uint8_t)fieldType) +
+    writeU32(out, (uint32_t)fieldId);
+}
+
+uint32_t TBinaryProtocol::writeFieldEnd(TTransport* out) const {
+  return 0;
+}
+
+uint32_t TBinaryProtocol::writeFieldStop(TTransport* out) const {
+  return
+    writeByte(out, (uint8_t)T_STOP);
+}  
+                               
+uint32_t TBinaryProtocol::writeMapBegin(TTransport* out,
+                                        const TType keyType,
+                                        const TType valType,
+                                        const uint32_t size) const {
+  return
+    writeByte(out, (uint8_t)keyType) +
+    writeByte(out, (uint8_t)valType) +
+    writeU32(out, size);
+}
+
+uint32_t TBinaryProtocol::writeMapEnd(TTransport* out) const {
+  return 0;
+}
+
+uint32_t TBinaryProtocol::writeListBegin(TTransport* out,
+                                         const TType elemType,
+                                         const uint32_t size) const {
+  return
+    writeByte(out, (uint8_t) elemType) +
+    writeU32(out, size);
+}
+
+uint32_t TBinaryProtocol::writeListEnd(TTransport* out) const {
+  return 0;
+}
+
+uint32_t TBinaryProtocol::writeSetBegin(TTransport* out,
+                                        const TType elemType,
+                                        const uint32_t size) const {
+  return
+    writeByte(out, (uint8_t)elemType) +
+    writeU32(out, size);
+}
+
+uint32_t TBinaryProtocol::writeSetEnd(TTransport* out) const {
+  return 0;
+}
+
+uint32_t TBinaryProtocol::writeByte(TTransport* out,
+                                    const uint8_t byte) const {
+  out->write(&byte, 1);
+  return 1;
+}
+
+uint32_t TBinaryProtocol::writeU32(TTransport* out,
+                                   const uint32_t u32) const {
+  uint32_t net = (uint32_t)htonl(u32);
+  out->write((uint8_t*)&net, 4);
+  return 4;
+}
+
+uint32_t TBinaryProtocol::writeI32(TTransport* out,
+                                   const int32_t i32) const {
+  int32_t net = (int32_t)htonl(i32);
+  out->write((uint8_t*)&net, 4);
+  return 4;
+}
+
+uint32_t TBinaryProtocol::writeU64(TTransport* out,
+                                   const uint64_t u64) const {
+  uint64_t net = (uint64_t)htonll(u64);
+  out->write((uint8_t*)&net, 8);
+  return 8;
+}
+
+uint32_t TBinaryProtocol::writeI64(TTransport* out,
+                                   const int64_t i64) const {
+  int64_t net = (int64_t)htonll(i64);
+  out->write((uint8_t*)&net, 8);
+  return 8;
+}
+
+uint32_t TBinaryProtocol::writeString(TTransport* out,
+                                      const string& str) const {
+  uint32_t result = writeU32(out, str.size());
+  out->write((uint8_t*)str.data(), str.size());
+  return result + str.size();
+}
+
+/**
+ * Reading functions
+ */
+
+uint32_t TBinaryProtocol::readStructBegin(TTransport* in,
+                                          string& name) const {
+  name = "";
+  return 0;
+}
+
+uint32_t TBinaryProtocol::readStructEnd(TTransport* in) const {
+  return 0;
+}
+
+uint32_t TBinaryProtocol::readFieldBegin(TTransport* in,
+                                         string& name,
+                                         TType& fieldType,
+                                         uint16_t& fieldId) const {
+  uint32_t result = 0;
+  uint8_t type;
+  result += readByte(in, type);
+  fieldType = (TType)type;
+  if (fieldType == T_STOP) {
+    fieldId = 0;
+    return result;
+  }
+  uint32_t id;
+  result += readU32(in, id);
+  fieldId = (uint16_t)id;
+  return result;
+}
   
-  if (buf.len < 4) {
-    return fieldMap;
-  }
-  uint32_t total_size = readU32(buf);
-  if (buf.len < total_size) {
-    // Data looks corrupt, we don't have that much, we will try to read what
-    // we can but be sure not to go over
-    total_size = buf.len;
-  }
-
-  // Field headers are 8 bytes, 4 byte fid + 4 byte length
-  while (total_size > 0 && buf.len > 8) {
-    uint32_t fid  = readU32(buf);
-    uint32_t flen = readU32(buf);
-    if (flen > buf.len) {
-      // flen corrupt, there isn't that much data left
-      break;
-    }
-    fieldMap.insert(make_pair(fid, TBuf(buf.data, flen)));
-    buf.data += flen;
-    buf.len  -= flen;
-    total_size -= 8 + flen;
-  }
-
-  return fieldMap;
+uint32_t TBinaryProtocol::readFieldEnd(TTransport* in) const {
+  return 0;
 }
-
-string TBinaryProtocol::writeStruct(const map<uint32_t,string>& s) const {
-  string result = "";
-  map<uint32_t,string>::const_iterator s_iter;
-  for (s_iter = s.begin(); s_iter != s.end(); ++s_iter) {
-    result += writeU32(s_iter->first);
-    result += writeU32(s_iter->second.size());
-    result += s_iter->second;
-  }
-  return writeU32(result.size()) + result;
-}
-
-string TBinaryProtocol::readString(TBuf& buf) const {
-  uint32_t len = readU32(buf);
-  if (len == 0) {
-    return "";
-  }
-  string result((const char*)(buf.data), len);
-  buf.data += len;
-  buf.len  -= len;
+ 
+uint32_t TBinaryProtocol::readMapBegin(TTransport* in,
+                                       TType& keyType,
+                                       TType& valType,
+                                       uint32_t& size) const {
+  uint8_t k, v;
+  uint32_t result = 0;
+  result += readByte(in, k);
+  keyType = (TType)k;
+  result += readByte(in, v);
+  valType = (TType)v;
+  result += readU32(in, size);
   return result;
 }
 
-uint8_t TBinaryProtocol::readByte(TBuf& buf) const {
-  if (buf.len == 0) {
-    return 0;
-  }
-  uint8_t result = (uint8_t)buf.data[0];
-  buf.data += 1;
-  buf.len  -= 1;
+uint32_t TBinaryProtocol::readMapEnd(TTransport* in) const {
+  return 0;
+}
+
+uint32_t TBinaryProtocol::readListBegin(TTransport* in,
+                                        TType& elemType,
+                                        uint32_t& size) const {
+  uint8_t e;
+  uint32_t result = 0;
+  result += readByte(in, e);
+  elemType = (TType)e;
+  result += readU32(in, size);
   return result;
 }
 
-uint32_t TBinaryProtocol::readU32(TBuf& buf) const {
-  if (buf.len < 4) {
-    return 0;
-  }
-  uint32_t result = *(uint32_t*)buf.data;
-  buf.data += 4;
-  buf.len  -= 4;
+uint32_t TBinaryProtocol::readListEnd(TTransport* in) const {
+  return 0;
+}
+
+uint32_t TBinaryProtocol::readSetBegin(TTransport* in,
+                                       TType& elemType,
+                                       uint32_t& size) const {
+  uint8_t e;
+  uint32_t result = 0;
+  result += readByte(in, e);
+  elemType = (TType)e;
+  result += readU32(in, size);
   return result;
 }
 
-int32_t TBinaryProtocol::readI32(TBuf& buf) const {
-  if (buf.len < 4) {
-    return 0;
-  }
-  int32_t result = *(int32_t*)buf.data;
-  buf.data += 4;
-  buf.len  -= 4;
-  return result; 
+uint32_t TBinaryProtocol::readSetEnd(TTransport* in) const {
+  return 0;
 }
 
-uint64_t TBinaryProtocol::readU64(TBuf& buf) const {
-  if (buf.len < 8) {
-    return 0;
-  }
-  uint64_t result = *(uint64_t*)buf.data;
-  buf.data += 8;
-  buf.len  -= 8;
-  return result;
+uint32_t TBinaryProtocol::readByte(TTransport* in,
+                                   uint8_t& byte) const {
+  uint8_t b[1];
+  in->readAll(b, 1);
+  byte = *(uint8_t*)b;
+  return 1;
 }
 
-int64_t TBinaryProtocol::readI64(TBuf& buf) const {
-  if (buf.len < 8) {
-    return 0;
-  }
-  int64_t result = *(int64_t*)buf.data;
-  buf.data += 8;
-  buf.len  -= 8;
-  return result;
+uint32_t TBinaryProtocol::readU32(TTransport* in,
+                                  uint32_t& u32) const {
+  uint8_t b[4];
+  in->readAll(b, 4);
+  u32 = *(uint32_t*)b;
+  u32 = (uint32_t)ntohl(u32);
+  return 4;
 }
 
-string TBinaryProtocol::writeString(const string& str) const {
-  uint32_t size = str.size();
-  string result = string((const char*)&size, 4);
-  return result + str;
+uint32_t TBinaryProtocol::readI32(TTransport* in,
+                                  int32_t& i32) const {
+  uint8_t b[4];
+  in->readAll(b, 4);
+  i32 = *(int32_t*)b;
+  i32 = (int32_t)ntohl(i32);
+  return 4;
 }
 
-string TBinaryProtocol::writeByte(const uint8_t byte) const {
-  return string((const char*)&byte, 1);
+uint32_t TBinaryProtocol::readU64(TTransport* in,
+                                  uint64_t& u64) const {
+  uint8_t b[8];
+  in->readAll(b, 8);
+  u64 = *(uint64_t*)b;
+  u64 = (uint64_t)ntohll(u64);
+  return 8;
 }
 
-string TBinaryProtocol::writeU32(const uint32_t u32) const {
-  return string((const char*)&u32, 4);
+uint32_t TBinaryProtocol::readI64(TTransport* in,
+                                  int64_t& i64) const {
+  uint8_t b[8];
+  in->readAll(b, 8);
+  i64 = *(int64_t*)b;
+  i64 = (int64_t)ntohll(i64);
+  return 8;
 }
 
-string TBinaryProtocol::writeI32(int32_t i32) const {
-  return string((const char*)&i32, 4);
-}
-
-string TBinaryProtocol::writeU64(uint64_t u64) const {
-  return string((const char*)&u64, 8);
-}
-
-string TBinaryProtocol::writeI64(int64_t i64) const {
-  return string((const char*)&i64, 8);
+uint32_t TBinaryProtocol::readString(TTransport* in,
+                                     string& str) const {
+  uint32_t size, result;
+  result = readU32(in, size);
+  uint8_t b[size];
+  in->readAll(b, size);
+  str = string((char*)b, size);
+  return result+size;
 }