blob: 89c7f48ceee53ab1a1ff2ad4ae269364db511dfb [file] [log] [blame]
Mark Sleef5f2be42006-09-05 21:05:31 +00001#ifndef _THRIFT_PROTOCOL_TPROTOCOL_H_
2#define _THRIFT_PROTOCOL_TPROTOCOL_H_ 1
Mark Sleee8540632006-05-30 09:24:40 +00003
Marc Slemko16698852006-08-04 03:16:10 +00004#include <transport/TTransport.h>
5
6#include <boost/shared_ptr.hpp>
7
Mark Slee8d7e1f62006-06-07 06:48:56 +00008#include <netinet/in.h>
Mark Sleee8540632006-05-30 09:24:40 +00009#include <sys/types.h>
10#include <string>
11#include <map>
12
Marc Slemko6f038a72006-08-03 18:58:09 +000013namespace facebook { namespace thrift { namespace protocol {
14
Marc Slemko16698852006-08-04 03:16:10 +000015using namespace boost;
16
Marc Slemko6f038a72006-08-03 18:58:09 +000017using namespace facebook::thrift::transport;
18
Mark Sleec98d0502006-09-06 02:42:25 +000019#define ntohll(x) (((uint64_t)(ntohl((int)((x & 0x00000000FFFFFFFF)))) << 32) | (uint32_t)ntohl(((int)(x >> 32 & 0x00000000FFFFFFFF))))
Mark Slee8d7e1f62006-06-07 06:48:56 +000020
21#define htonll(x) ntohll(x)
22
Mark Sleef5f2be42006-09-05 21:05:31 +000023// Forward declaration for TProtocol
Mark Sleee8540632006-05-30 09:24:40 +000024struct TBuf;
25
26/**
Mark Slee8d7e1f62006-06-07 06:48:56 +000027 * Enumerated definition of the types that the Thrift protocol supports.
28 * Take special note of the T_END type which is used specifically to mark
29 * the end of a sequence of fields.
30 */
31enum TType {
Marc Slemkod42a2c22006-08-10 03:30:18 +000032 T_STOP = 0,
Marc Slemko5b126d62006-08-11 23:03:42 +000033 T_VOID = 1,
34 T_BOOL = 2,
35 T_BYTE = 3,
Mark Sleecfc01932006-09-01 22:18:16 +000036 T_I08 = 3,
Marc Slemko5b126d62006-08-11 23:03:42 +000037 T_I16 = 6,
Marc Slemko5b126d62006-08-11 23:03:42 +000038 T_I32 = 8,
39 T_U64 = 9,
40 T_I64 = 10,
Mark Sleec98d0502006-09-06 02:42:25 +000041 T_DOUBLE = 4,
Marc Slemko5b126d62006-08-11 23:03:42 +000042 T_STRING = 11,
Marc Slemkod97eb612006-08-24 23:37:36 +000043 T_UTF7 = 11,
44 T_STRUCT = 12,
45 T_MAP = 13,
46 T_SET = 14,
47 T_LIST = 15,
48 T_UTF8 = 16,
49 T_UTF16 = 17
Mark Slee8d7e1f62006-06-07 06:48:56 +000050};
51
52/**
Mark Sleef5f2be42006-09-05 21:05:31 +000053 * Enumerated definition of the message types that the Thrift protocol
54 * supports.
Marc Slemko16698852006-08-04 03:16:10 +000055 */
56enum TMessageType {
57 T_CALL = 1,
58 T_REPLY = 2
59};
60
61/**
Mark Sleee8540632006-05-30 09:24:40 +000062 * Abstract class for a thrift protocol driver. These are all the methods that
63 * a protocol must implement. Essentially, there must be some way of reading
64 * and writing all the base types, plus a mechanism for writing out structs
65 * with indexed fields. Also notice that all methods are strictly const. This
66 * is by design. Protcol impelementations may NOT keep state, because the
67 * same TProtocol object may be used simultaneously by multiple threads. This
68 * theoretically introduces some limititations into the possible protocol
69 * formats, but with the benefit of performance, clarity, and simplicity.
70 *
71 * @author Mark Slee <mcslee@facebook.com>
72 */
73class TProtocol {
74 public:
75 virtual ~TProtocol() {}
76
77 /**
Mark Slee8d7e1f62006-06-07 06:48:56 +000078 * Writing functions.
Mark Sleee8540632006-05-30 09:24:40 +000079 */
80
Marc Slemko0b4ffa92006-08-11 02:49:29 +000081 virtual uint32_t writeMessageBegin(shared_ptr<TTransport> out,
Marc Slemko91f67482006-08-11 23:58:57 +000082 const std::string name,
Marc Slemko0b4ffa92006-08-11 02:49:29 +000083 const TMessageType messageType,
Mark Sleecfc01932006-09-01 22:18:16 +000084 const int32_t seqid) const = 0;
Marc Slemko16698852006-08-04 03:16:10 +000085
Marc Slemko0b4ffa92006-08-11 02:49:29 +000086 virtual uint32_t writeMessageEnd(shared_ptr<TTransport> out) const = 0;
Marc Slemko16698852006-08-04 03:16:10 +000087
88
Marc Slemko0b4ffa92006-08-11 02:49:29 +000089 virtual uint32_t writeStructBegin(shared_ptr<TTransport> out,
90 const std::string& name) const = 0;
91
92 virtual uint32_t writeStructEnd(shared_ptr<TTransport> out) const = 0;
93
94 virtual uint32_t writeFieldBegin(shared_ptr<TTransport> out,
95 const std::string& name,
96 const TType fieldType,
97 const int16_t fieldId) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +000098
Marc Slemko0b4ffa92006-08-11 02:49:29 +000099 virtual uint32_t writeFieldEnd(shared_ptr<TTransport> out) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000100
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000101 virtual uint32_t writeFieldStop(shared_ptr<TTransport> out) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000102
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000103 virtual uint32_t writeMapBegin(shared_ptr<TTransport> out,
104 const TType keyType,
105 const TType valType,
Marc Slemkob09f5882006-08-23 22:03:34 +0000106 const uint32_t size) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000107
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000108 virtual uint32_t writeMapEnd(shared_ptr<TTransport> out) const = 0;
109
110 virtual uint32_t writeListBegin(shared_ptr<TTransport> out,
111 const TType elemType,
Marc Slemkob09f5882006-08-23 22:03:34 +0000112 const uint32_t size) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000113
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000114 virtual uint32_t writeListEnd(shared_ptr<TTransport> out) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000115
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000116 virtual uint32_t writeSetBegin(shared_ptr<TTransport> out,
117 const TType elemType,
Marc Slemkob09f5882006-08-23 22:03:34 +0000118 const uint32_t size) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000119
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000120 virtual uint32_t writeSetEnd(shared_ptr<TTransport> out) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000121
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000122 virtual uint32_t writeBool(shared_ptr<TTransport> out,
123 const bool value) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000124
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000125 virtual uint32_t writeByte(shared_ptr<TTransport> out,
Mark Sleecfc01932006-09-01 22:18:16 +0000126 const int8_t byte) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000127
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000128 virtual uint32_t writeI16(shared_ptr<TTransport> out,
129 const int16_t i16) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000130
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000131 virtual uint32_t writeI32(shared_ptr<TTransport> out,
132 const int32_t i32) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000133
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000134 virtual uint32_t writeI64(shared_ptr<TTransport> out,
135 const int64_t i64) const = 0;
136
Mark Sleec98d0502006-09-06 02:42:25 +0000137 virtual uint32_t writeDouble(shared_ptr<TTransport> out,
138 const double dub) const = 0;
139
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000140 virtual uint32_t writeString(shared_ptr<TTransport> out,
141 const std::string& str) const = 0;
Mark Sleee8540632006-05-30 09:24:40 +0000142
143 /**
Mark Slee8d7e1f62006-06-07 06:48:56 +0000144 * Reading functions
Mark Sleee8540632006-05-30 09:24:40 +0000145 */
146
Marc Slemko5b126d62006-08-11 23:03:42 +0000147 virtual uint32_t readMessageBegin(shared_ptr<TTransport> in,
Marc Slemko91f67482006-08-11 23:58:57 +0000148 std::string& name,
149 TMessageType& messageType,
Mark Sleecfc01932006-09-01 22:18:16 +0000150 int32_t& seqid) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000151
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000152 virtual uint32_t readMessageEnd(shared_ptr<TTransport> in) const = 0;
153
154 virtual uint32_t readStructBegin(shared_ptr<TTransport> in,
155 std::string& name) const = 0;
156
157 virtual uint32_t readStructEnd(shared_ptr<TTransport> in) const = 0;
158
159 virtual uint32_t readFieldBegin(shared_ptr<TTransport> in,
160 std::string& name,
161 TType& fieldType,
162 int16_t& fieldId) const = 0;
163
164 virtual uint32_t readFieldEnd(shared_ptr<TTransport> in) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000165
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000166 virtual uint32_t readMapBegin(shared_ptr<TTransport> in,
167 TType& keyType,
168 TType& valType,
Marc Slemkob09f5882006-08-23 22:03:34 +0000169 uint32_t& size) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000170
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000171 virtual uint32_t readMapEnd(shared_ptr<TTransport> in) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000172
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000173 virtual uint32_t readListBegin(shared_ptr<TTransport> in,
174 TType& elemType,
Marc Slemkob09f5882006-08-23 22:03:34 +0000175 uint32_t& size) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000176
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000177 virtual uint32_t readListEnd(shared_ptr<TTransport> in) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000178
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000179 virtual uint32_t readSetBegin(shared_ptr<TTransport> in,
180 TType& elemType,
Marc Slemkob09f5882006-08-23 22:03:34 +0000181 uint32_t& size) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000182
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000183 virtual uint32_t readSetEnd(shared_ptr<TTransport> in) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000184
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000185 virtual uint32_t readBool(shared_ptr<TTransport> in,
186 bool& value) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000187
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000188 virtual uint32_t readByte(shared_ptr<TTransport> in,
Mark Sleecfc01932006-09-01 22:18:16 +0000189 int8_t& byte) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000190
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000191 virtual uint32_t readI16(shared_ptr<TTransport> in,
192 int16_t& i16) const = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000193
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000194 virtual uint32_t readI32(shared_ptr<TTransport> in,
195 int32_t& i32) const = 0;
196
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000197 virtual uint32_t readI64(shared_ptr<TTransport> in,
198 int64_t& i64) const = 0;
199
Mark Sleec98d0502006-09-06 02:42:25 +0000200 virtual uint32_t readDouble(shared_ptr<TTransport> in,
201 double& dub) const = 0;
202
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000203 virtual uint32_t readString(shared_ptr<TTransport> in,
204 std::string& str) const = 0;
Mark Sleee8540632006-05-30 09:24:40 +0000205
206 /**
Mark Slee8d7e1f62006-06-07 06:48:56 +0000207 * Method to arbitrarily skip over data.
Mark Sleee8540632006-05-30 09:24:40 +0000208 */
Marc Slemko16698852006-08-04 03:16:10 +0000209 uint32_t skip(shared_ptr<TTransport> in, TType type) const {
Mark Slee8d7e1f62006-06-07 06:48:56 +0000210 switch (type) {
Mark Slee78f58e22006-09-02 04:17:07 +0000211 case T_BOOL:
212 {
213 bool boolv;
214 return readBool(in, boolv);
215 }
Mark Slee8d7e1f62006-06-07 06:48:56 +0000216 case T_BYTE:
217 {
Mark Slee78f58e22006-09-02 04:17:07 +0000218 int8_t bytev;
219 return readByte(in, bytev);
Mark Slee8d7e1f62006-06-07 06:48:56 +0000220 }
Mark Sleecfc01932006-09-01 22:18:16 +0000221 case T_I16:
Mark Slee8d7e1f62006-06-07 06:48:56 +0000222 {
Mark Sleecfc01932006-09-01 22:18:16 +0000223 int16_t i16;
224 return readI16(in, i16);
Mark Slee8d7e1f62006-06-07 06:48:56 +0000225 }
226 case T_I32:
227 {
228 int32_t i32;
229 return readI32(in, i32);
230 }
Mark Slee8d7e1f62006-06-07 06:48:56 +0000231 case T_I64:
232 {
233 int64_t i64;
234 return readI64(in, i64);
235 }
Mark Sleec98d0502006-09-06 02:42:25 +0000236 case T_DOUBLE:
237 {
238 double dub;
239 return readDouble(in, dub);
240 }
Mark Slee8d7e1f62006-06-07 06:48:56 +0000241 case T_STRING:
242 {
243 std::string str;
244 return readString(in, str);
245 }
246 case T_STRUCT:
247 {
248 uint32_t result = 0;
249 std::string name;
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000250 int16_t fid;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000251 TType ftype;
252 result += readStructBegin(in, name);
253 while (true) {
254 result += readFieldBegin(in, name, ftype, fid);
255 if (ftype == T_STOP) {
256 break;
257 }
258 result += skip(in, ftype);
259 result += readFieldEnd(in);
260 }
261 result += readStructEnd(in);
262 return result;
263 }
264 case T_MAP:
265 {
266 uint32_t result = 0;
267 TType keyType;
268 TType valType;
Marc Slemkob09f5882006-08-23 22:03:34 +0000269 uint32_t i, size;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000270 result += readMapBegin(in, keyType, valType, size);
271 for (i = 0; i < size; i++) {
272 result += skip(in, keyType);
273 result += skip(in, valType);
274 }
275 result += readMapEnd(in);
276 return result;
277 }
278 case T_SET:
279 {
280 uint32_t result = 0;
281 TType elemType;
Marc Slemkob09f5882006-08-23 22:03:34 +0000282 uint32_t i, size;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000283 result += readSetBegin(in, elemType, size);
284 for (i = 0; i < size; i++) {
285 result += skip(in, elemType);
286 }
287 result += readSetEnd(in);
288 return result;
289 }
290 case T_LIST:
291 {
292 uint32_t result = 0;
293 TType elemType;
Marc Slemkob09f5882006-08-23 22:03:34 +0000294 uint32_t i, size;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000295 result += readListBegin(in, elemType, size);
296 for (i = 0; i < size; i++) {
297 result += skip(in, elemType);
298 }
299 result += readListEnd(in);
300 return result;
301 }
302 default:
303 return 0;
304 }
305 }
Mark Sleee8540632006-05-30 09:24:40 +0000306
307 protected:
308 TProtocol() {}
309};
310
Marc Slemko6f038a72006-08-03 18:58:09 +0000311}}} // facebook::thrift::protocol
312
Mark Sleef5f2be42006-09-05 21:05:31 +0000313#endif // #define _THRIFT_PROTOCOL_TPROTOCOL_H_ 1