blob: 5d440431bc9d259629a650e74ae82fbe3618642b [file] [log] [blame]
David Reissea2cba82009-03-30 21:35:00 +00001/*
2 * Licensed to the Apache Software Foundation (ASF) under one
3 * or more contributor license agreements. See the NOTICE file
4 * distributed with this work for additional information
5 * regarding copyright ownership. The ASF licenses this file
6 * to you under the Apache License, Version 2.0 (the
7 * "License"); you may not use this file except in compliance
8 * with the License. You may obtain a copy of the License at
9 *
10 * http://www.apache.org/licenses/LICENSE-2.0
11 *
12 * Unless required by applicable law or agreed to in writing,
13 * software distributed under the License is distributed on an
14 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
15 * KIND, either express or implied. See the License for the
16 * specific language governing permissions and limitations
17 * under the License.
18 */
Mark Slee9f0c6512007-02-28 23:58:26 +000019
Mark Sleef5f2be42006-09-05 21:05:31 +000020#ifndef _THRIFT_PROTOCOL_TPROTOCOL_H_
21#define _THRIFT_PROTOCOL_TPROTOCOL_H_ 1
Mark Sleee8540632006-05-30 09:24:40 +000022
Roger Meier49ff8b12012-04-13 09:12:31 +000023#include <thrift/transport/TTransport.h>
24#include <thrift/protocol/TProtocolException.h>
Marc Slemko16698852006-08-04 03:16:10 +000025
26#include <boost/shared_ptr.hpp>
David Reisse4d4ea02009-04-02 21:37:17 +000027#include <boost/static_assert.hpp>
Marc Slemko16698852006-08-04 03:16:10 +000028
Roger Meier2fa9c312011-09-05 19:15:53 +000029#ifdef HAVE_NETINET_IN_H
Mark Slee8d7e1f62006-06-07 06:48:56 +000030#include <netinet/in.h>
Roger Meier2fa9c312011-09-05 19:15:53 +000031#endif
Mark Sleee8540632006-05-30 09:24:40 +000032#include <sys/types.h>
33#include <string>
34#include <map>
David Reiss8dfc7322010-10-06 17:09:58 +000035#include <vector>
Mark Sleee8540632006-05-30 09:24:40 +000036
David Reisse4d4ea02009-04-02 21:37:17 +000037// Use this to get around strict aliasing rules.
38// For example, uint64_t i = bitwise_cast<uint64_t>(returns_double());
39// The most obvious implementation is to just cast a pointer,
40// but that doesn't work.
41// For a pretty in-depth explanation of the problem, see
42// http://www.cellperformance.com/mike_acton/2006/06/ (...)
43// understanding_strict_aliasing.html
44template <typename To, typename From>
45static inline To bitwise_cast(From from) {
46 BOOST_STATIC_ASSERT(sizeof(From) == sizeof(To));
47
48 // BAD!!! These are all broken with -O2.
49 //return *reinterpret_cast<To*>(&from); // BAD!!!
50 //return *static_cast<To*>(static_cast<void*>(&from)); // BAD!!!
51 //return *(To*)(void*)&from; // BAD!!!
52
53 // Super clean and paritally blessed by section 3.9 of the standard.
54 //unsigned char c[sizeof(from)];
55 //memcpy(c, &from, sizeof(from));
56 //To to;
57 //memcpy(&to, c, sizeof(c));
58 //return to;
59
60 // Slightly more questionable.
61 // Same code emitted by GCC.
62 //To to;
63 //memcpy(&to, &from, sizeof(from));
64 //return to;
65
66 // Technically undefined, but almost universally supported,
67 // and the most efficient implementation.
68 union {
69 From f;
70 To t;
71 } u;
72 u.f = from;
73 return u.t;
74}
75
76
Jake Farrellc1fe30b2011-06-01 20:34:26 +000077#ifdef HAVE_SYS_PARAM_H
Bryan Duxbury184d2622010-08-17 17:43:58 +000078#include <sys/param.h>
Mark Slee4f261c52007-04-13 00:33:24 +000079#endif
80
Roger Meierf9f841d2012-06-19 20:42:33 +000081#ifndef __THRIFT_BYTE_ORDER
Mark Slee1d2ead32007-06-09 01:23:04 +000082# if defined(BYTE_ORDER) && defined(LITTLE_ENDIAN) && defined(BIG_ENDIAN)
Roger Meierf9f841d2012-06-19 20:42:33 +000083# define __THRIFT_BYTE_ORDER BYTE_ORDER
84# define __THRIFT_LITTLE_ENDIAN LITTLE_ENDIAN
85# define __THRIFT_BIG_ENDIAN BIG_ENDIAN
Mark Slee1d2ead32007-06-09 01:23:04 +000086# else
David Reiss9b903442009-10-21 05:51:28 +000087# include <boost/config.hpp>
Roger Meiera93848b2011-09-12 22:20:11 +000088# include <boost/detail/endian.hpp>
Roger Meierf9f841d2012-06-19 20:42:33 +000089# define __THRIFT_BYTE_ORDER BOOST_BYTE_ORDER
Roger Meiera93848b2011-09-12 22:20:11 +000090# ifdef BOOST_LITTLE_ENDIAN
Roger Meierf9f841d2012-06-19 20:42:33 +000091# define __THRIFT_LITTLE_ENDIAN __THRIFT_BYTE_ORDER
92# define __THRIFT_BIG_ENDIAN 0
Roger Meiera93848b2011-09-12 22:20:11 +000093# else
Roger Meierf9f841d2012-06-19 20:42:33 +000094# define __THRIFT_LITTLE_ENDIAN 0
95# define __THRIFT_BIG_ENDIAN __THRIFT_BYTE_ORDER
Roger Meiera93848b2011-09-12 22:20:11 +000096# endif
Mark Slee1d2ead32007-06-09 01:23:04 +000097# endif
98#endif
99
Roger Meierf9f841d2012-06-19 20:42:33 +0000100#if __THRIFT_BYTE_ORDER == __THRIFT_BIG_ENDIAN
David Reisse4d4ea02009-04-02 21:37:17 +0000101# define ntohll(n) (n)
102# define htonll(n) (n)
103# if defined(__GNUC__) && defined(__GLIBC__)
104# include <byteswap.h>
105# define htolell(n) bswap_64(n)
106# define letohll(n) bswap_64(n)
107# else /* GNUC & GLIBC */
108# define bswap_64(n) \
109 ( (((n) & 0xff00000000000000ull) >> 56) \
110 | (((n) & 0x00ff000000000000ull) >> 40) \
111 | (((n) & 0x0000ff0000000000ull) >> 24) \
112 | (((n) & 0x000000ff00000000ull) >> 8) \
113 | (((n) & 0x00000000ff000000ull) << 8) \
114 | (((n) & 0x0000000000ff0000ull) << 24) \
115 | (((n) & 0x000000000000ff00ull) << 40) \
116 | (((n) & 0x00000000000000ffull) << 56) )
David Reiss30297862009-08-05 16:42:59 +0000117# define htolell(n) bswap_64(n)
118# define letohll(n) bswap_64(n)
David Reisse4d4ea02009-04-02 21:37:17 +0000119# endif /* GNUC & GLIBC */
Roger Meierf9f841d2012-06-19 20:42:33 +0000120#elif __THRIFT_BYTE_ORDER == __THRIFT_LITTLE_ENDIAN
David Reisse4d4ea02009-04-02 21:37:17 +0000121# define htolell(n) (n)
122# define letohll(n) (n)
Mark Slee4f261c52007-04-13 00:33:24 +0000123# if defined(__GNUC__) && defined(__GLIBC__)
124# include <byteswap.h>
125# define ntohll(n) bswap_64(n)
126# define htonll(n) bswap_64(n)
Roger Meierb69d24d2012-10-04 18:02:15 +0000127# elif defined(_MSC_VER) /* Microsoft Visual C++ */
128# define ntohll(n) ( _byteswap_uint64((uint64_t)n) )
129# define htonll(n) ( _byteswap_uint64((uint64_t)n) )
Konrad Grochowski38bf2342014-12-20 13:23:27 +0100130# elif !defined(ntohll) /* Not GNUC/GLIBC or MSVC */
Roger Meier82525772012-11-16 00:38:27 +0000131# define ntohll(n) ( (((uint64_t)ntohl((uint32_t)n)) << 32) + ntohl((uint32_t)(n >> 32)) )
132# define htonll(n) ( (((uint64_t)htonl((uint32_t)n)) << 32) + htonl((uint32_t)(n >> 32)) )
Roger Meierb69d24d2012-10-04 18:02:15 +0000133# endif /* GNUC/GLIBC or MSVC or something else */
Roger Meierf9f841d2012-06-19 20:42:33 +0000134#else /* __THRIFT_BYTE_ORDER */
Mark Slee4f261c52007-04-13 00:33:24 +0000135# error "Can't define htonll or ntohll!"
Mark Sleedc8a2a22006-09-19 22:20:18 +0000136#endif
Mark Slee8d7e1f62006-06-07 06:48:56 +0000137
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100138namespace apache {
139namespace thrift {
140namespace protocol {
Ben Craigf4e6e622013-11-05 19:49:12 -0600141
142using apache::thrift::transport::TTransport;
143
Mark Sleee8540632006-05-30 09:24:40 +0000144/**
Mark Slee8d7e1f62006-06-07 06:48:56 +0000145 * Enumerated definition of the types that the Thrift protocol supports.
146 * Take special note of the T_END type which is used specifically to mark
147 * the end of a sequence of fields.
148 */
149enum TType {
Marc Slemkod42a2c22006-08-10 03:30:18 +0000150 T_STOP = 0,
Marc Slemko5b126d62006-08-11 23:03:42 +0000151 T_VOID = 1,
152 T_BOOL = 2,
153 T_BYTE = 3,
Mark Sleecfc01932006-09-01 22:18:16 +0000154 T_I08 = 3,
Marc Slemko5b126d62006-08-11 23:03:42 +0000155 T_I16 = 6,
Marc Slemko5b126d62006-08-11 23:03:42 +0000156 T_I32 = 8,
157 T_U64 = 9,
158 T_I64 = 10,
Mark Sleec98d0502006-09-06 02:42:25 +0000159 T_DOUBLE = 4,
Marc Slemko5b126d62006-08-11 23:03:42 +0000160 T_STRING = 11,
Marc Slemkod97eb612006-08-24 23:37:36 +0000161 T_UTF7 = 11,
162 T_STRUCT = 12,
163 T_MAP = 13,
164 T_SET = 14,
165 T_LIST = 15,
166 T_UTF8 = 16,
167 T_UTF16 = 17
Mark Slee8d7e1f62006-06-07 06:48:56 +0000168};
169
170/**
Mark Sleef5f2be42006-09-05 21:05:31 +0000171 * Enumerated definition of the message types that the Thrift protocol
172 * supports.
Marc Slemko16698852006-08-04 03:16:10 +0000173 */
174enum TMessageType {
175 T_CALL = 1,
Mark Sleef9831082007-02-20 20:59:21 +0000176 T_REPLY = 2,
David Reissdeda1412009-04-02 19:22:31 +0000177 T_EXCEPTION = 3,
178 T_ONEWAY = 4
Marc Slemko16698852006-08-04 03:16:10 +0000179};
180
David Reiss6806fb82010-10-06 17:09:52 +0000181
182/**
183 * Helper template for implementing TProtocol::skip().
184 *
185 * Templatized to avoid having to make virtual function calls.
186 */
187template <class Protocol_>
188uint32_t skip(Protocol_& prot, TType type) {
189 switch (type) {
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100190 case T_BOOL: {
191 bool boolv;
192 return prot.readBool(boolv);
193 }
194 case T_BYTE: {
195 int8_t bytev;
196 return prot.readByte(bytev);
197 }
198 case T_I16: {
199 int16_t i16;
200 return prot.readI16(i16);
201 }
202 case T_I32: {
203 int32_t i32;
204 return prot.readI32(i32);
205 }
206 case T_I64: {
207 int64_t i64;
208 return prot.readI64(i64);
209 }
210 case T_DOUBLE: {
211 double dub;
212 return prot.readDouble(dub);
213 }
214 case T_STRING: {
215 std::string str;
216 return prot.readBinary(str);
217 }
218 case T_STRUCT: {
219 uint32_t result = 0;
220 std::string name;
221 int16_t fid;
222 TType ftype;
223 result += prot.readStructBegin(name);
224 while (true) {
225 result += prot.readFieldBegin(name, ftype, fid);
226 if (ftype == T_STOP) {
227 break;
David Reiss6806fb82010-10-06 17:09:52 +0000228 }
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100229 result += skip(prot, ftype);
230 result += prot.readFieldEnd();
David Reiss6806fb82010-10-06 17:09:52 +0000231 }
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100232 result += prot.readStructEnd();
233 return result;
234 }
235 case T_MAP: {
236 uint32_t result = 0;
237 TType keyType;
238 TType valType;
239 uint32_t i, size;
240 result += prot.readMapBegin(keyType, valType, size);
241 for (i = 0; i < size; i++) {
242 result += skip(prot, keyType);
243 result += skip(prot, valType);
David Reiss6806fb82010-10-06 17:09:52 +0000244 }
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100245 result += prot.readMapEnd();
246 return result;
247 }
248 case T_SET: {
249 uint32_t result = 0;
250 TType elemType;
251 uint32_t i, size;
252 result += prot.readSetBegin(elemType, size);
253 for (i = 0; i < size; i++) {
254 result += skip(prot, elemType);
David Reiss6806fb82010-10-06 17:09:52 +0000255 }
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100256 result += prot.readSetEnd();
257 return result;
258 }
259 case T_LIST: {
260 uint32_t result = 0;
261 TType elemType;
262 uint32_t i, size;
263 result += prot.readListBegin(elemType, size);
264 for (i = 0; i < size; i++) {
265 result += skip(prot, elemType);
David Reiss6806fb82010-10-06 17:09:52 +0000266 }
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100267 result += prot.readListEnd();
268 return result;
269 }
270 case T_STOP:
271 case T_VOID:
272 case T_U64:
273 case T_UTF8:
274 case T_UTF16:
Roger Meierc0b5d902010-11-30 20:23:44 +0000275 break;
David Reiss6806fb82010-10-06 17:09:52 +0000276 }
Roger Meierc0b5d902010-11-30 20:23:44 +0000277 return 0;
David Reiss6806fb82010-10-06 17:09:52 +0000278}
279
Jens Geyer885c6792014-05-02 21:31:55 +0200280static const uint32_t DEFAULT_RECURSION_LIMIT = 64;
281
Marc Slemko16698852006-08-04 03:16:10 +0000282/**
Mark Sleee8540632006-05-30 09:24:40 +0000283 * Abstract class for a thrift protocol driver. These are all the methods that
284 * a protocol must implement. Essentially, there must be some way of reading
285 * and writing all the base types, plus a mechanism for writing out structs
Mark Slee5d06fea2007-03-05 22:18:18 +0000286 * with indexed fields.
287 *
288 * TProtocol objects should not be shared across multiple encoding contexts,
289 * as they may need to maintain internal state in some protocols (i.e. XML).
290 * Note that is is acceptable for the TProtocol module to do its own internal
291 * buffered reads/writes to the underlying TTransport where appropriate (i.e.
292 * when parsing an input XML stream, reading should be batched rather than
293 * looking ahead character by character for a close tag).
Mark Sleee8540632006-05-30 09:24:40 +0000294 *
Mark Sleee8540632006-05-30 09:24:40 +0000295 */
296class TProtocol {
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100297public:
Mark Sleee8540632006-05-30 09:24:40 +0000298 virtual ~TProtocol() {}
299
300 /**
Mark Slee8d7e1f62006-06-07 06:48:56 +0000301 * Writing functions.
Mark Sleee8540632006-05-30 09:24:40 +0000302 */
303
David Reiss6806fb82010-10-06 17:09:52 +0000304 virtual uint32_t writeMessageBegin_virt(const std::string& name,
305 const TMessageType messageType,
306 const int32_t seqid) = 0;
Marc Slemko16698852006-08-04 03:16:10 +0000307
David Reiss6806fb82010-10-06 17:09:52 +0000308 virtual uint32_t writeMessageEnd_virt() = 0;
Marc Slemko16698852006-08-04 03:16:10 +0000309
David Reiss6806fb82010-10-06 17:09:52 +0000310 virtual uint32_t writeStructBegin_virt(const char* name) = 0;
David Reiss0c90f6f2008-02-06 22:18:40 +0000311
David Reiss6806fb82010-10-06 17:09:52 +0000312 virtual uint32_t writeStructEnd_virt() = 0;
David Reiss0c90f6f2008-02-06 22:18:40 +0000313
David Reiss6806fb82010-10-06 17:09:52 +0000314 virtual uint32_t writeFieldBegin_virt(const char* name,
315 const TType fieldType,
316 const int16_t fieldId) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000317
David Reiss6806fb82010-10-06 17:09:52 +0000318 virtual uint32_t writeFieldEnd_virt() = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000319
David Reiss6806fb82010-10-06 17:09:52 +0000320 virtual uint32_t writeFieldStop_virt() = 0;
David Reiss0c90f6f2008-02-06 22:18:40 +0000321
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100322 virtual uint32_t writeMapBegin_virt(const TType keyType, const TType valType, const uint32_t size)
323 = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000324
David Reiss6806fb82010-10-06 17:09:52 +0000325 virtual uint32_t writeMapEnd_virt() = 0;
David Reiss0c90f6f2008-02-06 22:18:40 +0000326
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100327 virtual uint32_t writeListBegin_virt(const TType elemType, const uint32_t size) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000328
David Reiss6806fb82010-10-06 17:09:52 +0000329 virtual uint32_t writeListEnd_virt() = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000330
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100331 virtual uint32_t writeSetBegin_virt(const TType elemType, const uint32_t size) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000332
David Reiss6806fb82010-10-06 17:09:52 +0000333 virtual uint32_t writeSetEnd_virt() = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000334
David Reiss6806fb82010-10-06 17:09:52 +0000335 virtual uint32_t writeBool_virt(const bool value) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000336
David Reiss6806fb82010-10-06 17:09:52 +0000337 virtual uint32_t writeByte_virt(const int8_t byte) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000338
David Reiss6806fb82010-10-06 17:09:52 +0000339 virtual uint32_t writeI16_virt(const int16_t i16) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000340
David Reiss6806fb82010-10-06 17:09:52 +0000341 virtual uint32_t writeI32_virt(const int32_t i32) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000342
David Reiss6806fb82010-10-06 17:09:52 +0000343 virtual uint32_t writeI64_virt(const int64_t i64) = 0;
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000344
David Reiss6806fb82010-10-06 17:09:52 +0000345 virtual uint32_t writeDouble_virt(const double dub) = 0;
Mark Sleec98d0502006-09-06 02:42:25 +0000346
David Reiss6806fb82010-10-06 17:09:52 +0000347 virtual uint32_t writeString_virt(const std::string& str) = 0;
Mark Sleee8540632006-05-30 09:24:40 +0000348
David Reiss6806fb82010-10-06 17:09:52 +0000349 virtual uint32_t writeBinary_virt(const std::string& str) = 0;
350
351 uint32_t writeMessageBegin(const std::string& name,
352 const TMessageType messageType,
353 const int32_t seqid) {
354 T_VIRTUAL_CALL();
355 return writeMessageBegin_virt(name, messageType, seqid);
356 }
357
358 uint32_t writeMessageEnd() {
359 T_VIRTUAL_CALL();
360 return writeMessageEnd_virt();
361 }
362
David Reiss6806fb82010-10-06 17:09:52 +0000363 uint32_t writeStructBegin(const char* name) {
364 T_VIRTUAL_CALL();
365 return writeStructBegin_virt(name);
366 }
367
368 uint32_t writeStructEnd() {
369 T_VIRTUAL_CALL();
370 return writeStructEnd_virt();
371 }
372
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100373 uint32_t writeFieldBegin(const char* name, const TType fieldType, const int16_t fieldId) {
David Reiss6806fb82010-10-06 17:09:52 +0000374 T_VIRTUAL_CALL();
375 return writeFieldBegin_virt(name, fieldType, fieldId);
376 }
377
378 uint32_t writeFieldEnd() {
379 T_VIRTUAL_CALL();
380 return writeFieldEnd_virt();
381 }
382
383 uint32_t writeFieldStop() {
384 T_VIRTUAL_CALL();
385 return writeFieldStop_virt();
386 }
387
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100388 uint32_t writeMapBegin(const TType keyType, const TType valType, const uint32_t size) {
David Reiss6806fb82010-10-06 17:09:52 +0000389 T_VIRTUAL_CALL();
390 return writeMapBegin_virt(keyType, valType, size);
391 }
392
393 uint32_t writeMapEnd() {
394 T_VIRTUAL_CALL();
395 return writeMapEnd_virt();
396 }
397
398 uint32_t writeListBegin(const TType elemType, const uint32_t size) {
399 T_VIRTUAL_CALL();
400 return writeListBegin_virt(elemType, size);
401 }
402
403 uint32_t writeListEnd() {
404 T_VIRTUAL_CALL();
405 return writeListEnd_virt();
406 }
407
408 uint32_t writeSetBegin(const TType elemType, const uint32_t size) {
409 T_VIRTUAL_CALL();
410 return writeSetBegin_virt(elemType, size);
411 }
412
413 uint32_t writeSetEnd() {
414 T_VIRTUAL_CALL();
415 return writeSetEnd_virt();
416 }
417
418 uint32_t writeBool(const bool value) {
419 T_VIRTUAL_CALL();
420 return writeBool_virt(value);
421 }
422
423 uint32_t writeByte(const int8_t byte) {
424 T_VIRTUAL_CALL();
425 return writeByte_virt(byte);
426 }
427
428 uint32_t writeI16(const int16_t i16) {
429 T_VIRTUAL_CALL();
430 return writeI16_virt(i16);
431 }
432
433 uint32_t writeI32(const int32_t i32) {
434 T_VIRTUAL_CALL();
435 return writeI32_virt(i32);
436 }
437
438 uint32_t writeI64(const int64_t i64) {
439 T_VIRTUAL_CALL();
440 return writeI64_virt(i64);
441 }
442
443 uint32_t writeDouble(const double dub) {
444 T_VIRTUAL_CALL();
445 return writeDouble_virt(dub);
446 }
447
448 uint32_t writeString(const std::string& str) {
449 T_VIRTUAL_CALL();
450 return writeString_virt(str);
451 }
452
453 uint32_t writeBinary(const std::string& str) {
454 T_VIRTUAL_CALL();
455 return writeBinary_virt(str);
456 }
David Reissc005b1b2008-02-15 01:38:18 +0000457
Mark Sleee8540632006-05-30 09:24:40 +0000458 /**
Mark Slee8d7e1f62006-06-07 06:48:56 +0000459 * Reading functions
Mark Sleee8540632006-05-30 09:24:40 +0000460 */
461
David Reiss6806fb82010-10-06 17:09:52 +0000462 virtual uint32_t readMessageBegin_virt(std::string& name,
463 TMessageType& messageType,
464 int32_t& seqid) = 0;
David Reiss0c90f6f2008-02-06 22:18:40 +0000465
David Reiss6806fb82010-10-06 17:09:52 +0000466 virtual uint32_t readMessageEnd_virt() = 0;
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000467
David Reiss6806fb82010-10-06 17:09:52 +0000468 virtual uint32_t readStructBegin_virt(std::string& name) = 0;
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000469
David Reiss6806fb82010-10-06 17:09:52 +0000470 virtual uint32_t readStructEnd_virt() = 0;
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000471
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100472 virtual uint32_t readFieldBegin_virt(std::string& name, TType& fieldType, int16_t& fieldId) = 0;
David Reiss0c90f6f2008-02-06 22:18:40 +0000473
David Reiss6806fb82010-10-06 17:09:52 +0000474 virtual uint32_t readFieldEnd_virt() = 0;
David Reiss0c90f6f2008-02-06 22:18:40 +0000475
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100476 virtual uint32_t readMapBegin_virt(TType& keyType, TType& valType, uint32_t& size) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000477
David Reiss6806fb82010-10-06 17:09:52 +0000478 virtual uint32_t readMapEnd_virt() = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000479
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100480 virtual uint32_t readListBegin_virt(TType& elemType, uint32_t& size) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000481
David Reiss6806fb82010-10-06 17:09:52 +0000482 virtual uint32_t readListEnd_virt() = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000483
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100484 virtual uint32_t readSetBegin_virt(TType& elemType, uint32_t& size) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000485
David Reiss6806fb82010-10-06 17:09:52 +0000486 virtual uint32_t readSetEnd_virt() = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000487
David Reiss6806fb82010-10-06 17:09:52 +0000488 virtual uint32_t readBool_virt(bool& value) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000489
David Reiss8dfc7322010-10-06 17:09:58 +0000490 virtual uint32_t readBool_virt(std::vector<bool>::reference value) = 0;
491
David Reiss6806fb82010-10-06 17:09:52 +0000492 virtual uint32_t readByte_virt(int8_t& byte) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000493
David Reiss6806fb82010-10-06 17:09:52 +0000494 virtual uint32_t readI16_virt(int16_t& i16) = 0;
Mark Slee8d7e1f62006-06-07 06:48:56 +0000495
David Reiss6806fb82010-10-06 17:09:52 +0000496 virtual uint32_t readI32_virt(int32_t& i32) = 0;
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000497
David Reiss6806fb82010-10-06 17:09:52 +0000498 virtual uint32_t readI64_virt(int64_t& i64) = 0;
Marc Slemko0b4ffa92006-08-11 02:49:29 +0000499
David Reiss6806fb82010-10-06 17:09:52 +0000500 virtual uint32_t readDouble_virt(double& dub) = 0;
Mark Sleec98d0502006-09-06 02:42:25 +0000501
David Reiss6806fb82010-10-06 17:09:52 +0000502 virtual uint32_t readString_virt(std::string& str) = 0;
Mark Sleee8540632006-05-30 09:24:40 +0000503
David Reiss6806fb82010-10-06 17:09:52 +0000504 virtual uint32_t readBinary_virt(std::string& str) = 0;
505
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100506 uint32_t readMessageBegin(std::string& name, TMessageType& messageType, int32_t& seqid) {
David Reiss6806fb82010-10-06 17:09:52 +0000507 T_VIRTUAL_CALL();
508 return readMessageBegin_virt(name, messageType, seqid);
509 }
510
511 uint32_t readMessageEnd() {
512 T_VIRTUAL_CALL();
513 return readMessageEnd_virt();
514 }
515
516 uint32_t readStructBegin(std::string& name) {
517 T_VIRTUAL_CALL();
518 return readStructBegin_virt(name);
519 }
520
521 uint32_t readStructEnd() {
522 T_VIRTUAL_CALL();
523 return readStructEnd_virt();
524 }
525
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100526 uint32_t readFieldBegin(std::string& name, TType& fieldType, int16_t& fieldId) {
David Reiss6806fb82010-10-06 17:09:52 +0000527 T_VIRTUAL_CALL();
528 return readFieldBegin_virt(name, fieldType, fieldId);
529 }
530
531 uint32_t readFieldEnd() {
532 T_VIRTUAL_CALL();
533 return readFieldEnd_virt();
534 }
535
536 uint32_t readMapBegin(TType& keyType, TType& valType, uint32_t& size) {
537 T_VIRTUAL_CALL();
538 return readMapBegin_virt(keyType, valType, size);
539 }
540
541 uint32_t readMapEnd() {
542 T_VIRTUAL_CALL();
543 return readMapEnd_virt();
544 }
545
546 uint32_t readListBegin(TType& elemType, uint32_t& size) {
547 T_VIRTUAL_CALL();
548 return readListBegin_virt(elemType, size);
549 }
550
551 uint32_t readListEnd() {
552 T_VIRTUAL_CALL();
553 return readListEnd_virt();
554 }
555
556 uint32_t readSetBegin(TType& elemType, uint32_t& size) {
557 T_VIRTUAL_CALL();
558 return readSetBegin_virt(elemType, size);
559 }
560
561 uint32_t readSetEnd() {
562 T_VIRTUAL_CALL();
563 return readSetEnd_virt();
564 }
565
566 uint32_t readBool(bool& value) {
567 T_VIRTUAL_CALL();
568 return readBool_virt(value);
569 }
570
571 uint32_t readByte(int8_t& byte) {
572 T_VIRTUAL_CALL();
573 return readByte_virt(byte);
574 }
575
576 uint32_t readI16(int16_t& i16) {
577 T_VIRTUAL_CALL();
578 return readI16_virt(i16);
579 }
580
581 uint32_t readI32(int32_t& i32) {
582 T_VIRTUAL_CALL();
583 return readI32_virt(i32);
584 }
585
586 uint32_t readI64(int64_t& i64) {
587 T_VIRTUAL_CALL();
588 return readI64_virt(i64);
589 }
590
591 uint32_t readDouble(double& dub) {
592 T_VIRTUAL_CALL();
593 return readDouble_virt(dub);
594 }
595
596 uint32_t readString(std::string& str) {
597 T_VIRTUAL_CALL();
598 return readString_virt(str);
599 }
600
601 uint32_t readBinary(std::string& str) {
602 T_VIRTUAL_CALL();
603 return readBinary_virt(str);
604 }
David Reissc005b1b2008-02-15 01:38:18 +0000605
David Reiss8dfc7322010-10-06 17:09:58 +0000606 /*
607 * std::vector is specialized for bool, and its elements are individual bits
608 * rather than bools. We need to define a different version of readBool()
609 * to work with std::vector<bool>.
610 */
611 uint32_t readBool(std::vector<bool>::reference value) {
612 T_VIRTUAL_CALL();
613 return readBool_virt(value);
David Reiss035aed92009-02-10 21:38:48 +0000614 }
615
Mark Sleee8540632006-05-30 09:24:40 +0000616 /**
Mark Slee8d7e1f62006-06-07 06:48:56 +0000617 * Method to arbitrarily skip over data.
Mark Sleee8540632006-05-30 09:24:40 +0000618 */
Mark Slee4af6ed72006-10-25 19:02:49 +0000619 uint32_t skip(TType type) {
David Reiss6806fb82010-10-06 17:09:52 +0000620 T_VIRTUAL_CALL();
621 return skip_virt(type);
622 }
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100623 virtual uint32_t skip_virt(TType type) { return ::apache::thrift::protocol::skip(*this, type); }
Mark Sleee8540632006-05-30 09:24:40 +0000624
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100625 inline boost::shared_ptr<TTransport> getTransport() { return ptrans_; }
Mark Slee4af6ed72006-10-25 19:02:49 +0000626
Aditya Agarwal9abb0d62007-01-24 22:53:54 +0000627 // TODO: remove these two calls, they are for backwards
628 // compatibility
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100629 inline boost::shared_ptr<TTransport> getInputTransport() { return ptrans_; }
630 inline boost::shared_ptr<TTransport> getOutputTransport() { return ptrans_; }
Mark Slee4af6ed72006-10-25 19:02:49 +0000631
Jens Geyer885c6792014-05-02 21:31:55 +0200632 void incrementRecursionDepth() {
633 if (recursion_limit_ < ++recursion_depth_) {
634 throw TProtocolException(TProtocolException::DEPTH_LIMIT);
635 }
Mark Slee43b6c632007-02-07 00:54:17 +0000636 }
David Reiss0c90f6f2008-02-06 22:18:40 +0000637
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100638 void decrementRecursionDepth() { --recursion_depth_; }
Jens Geyer885c6792014-05-02 21:31:55 +0200639
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100640protected:
Jens Geyer885c6792014-05-02 21:31:55 +0200641 TProtocol(boost::shared_ptr<TTransport> ptrans)
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100642 : ptrans_(ptrans), recursion_depth_(0), recursion_limit_(DEFAULT_RECURSION_LIMIT) {}
Jens Geyer885c6792014-05-02 21:31:55 +0200643
Mark Slee5ea15f92007-03-05 22:55:59 +0000644 boost::shared_ptr<TTransport> ptrans_;
Mark Slee4af6ed72006-10-25 19:02:49 +0000645
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100646private:
Mark Sleee8540632006-05-30 09:24:40 +0000647 TProtocol() {}
Jens Geyer885c6792014-05-02 21:31:55 +0200648 uint32_t recursion_depth_;
649 uint32_t recursion_limit_;
Mark Sleee8540632006-05-30 09:24:40 +0000650};
651
Mark Slee4af6ed72006-10-25 19:02:49 +0000652/**
653 * Constructs input and output protocol objects given transports.
654 */
655class TProtocolFactory {
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100656public:
Mark Slee4af6ed72006-10-25 19:02:49 +0000657 TProtocolFactory() {}
658
659 virtual ~TProtocolFactory() {}
660
Aditya Agarwal9abb0d62007-01-24 22:53:54 +0000661 virtual boost::shared_ptr<TProtocol> getProtocol(boost::shared_ptr<TTransport> trans) = 0;
Mark Slee4af6ed72006-10-25 19:02:49 +0000662};
663
David Reissb7762a02010-10-06 17:10:00 +0000664/**
665 * Dummy protocol class.
666 *
667 * This class does nothing, and should never be instantiated.
668 * It is used only by the generator code.
669 */
Konrad Grochowski16a23a62014-11-13 15:33:38 +0100670class TDummyProtocol : public TProtocol {};
671}
672}
673} // apache::thrift::protocol
Marc Slemko6f038a72006-08-03 18:58:09 +0000674
Mark Sleef5f2be42006-09-05 21:05:31 +0000675#endif // #define _THRIFT_PROTOCOL_TPROTOCOL_H_ 1