blob: c6b1a00a56384e15b7f0dfc93192aa32ec4a4d2a [file] [log] [blame]
Jens Geyerd5436f52014-10-03 19:50:38 +02001(*
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 *)
19
20{$SCOPEDENUMS ON}
21
22unit Thrift.Protocol;
23
24interface
25
26uses
27 Classes,
28 SysUtils,
29 Contnrs,
Jens Geyer606f1ef2018-04-09 23:09:41 +020030 Thrift.Exception,
Jens Geyerd5436f52014-10-03 19:50:38 +020031 Thrift.Stream,
Jens Geyer8f7487e2019-05-09 22:21:32 +020032 Thrift.Utils,
Jens Geyerd5436f52014-10-03 19:50:38 +020033 Thrift.Collections,
Jens Geyera019cda2019-11-09 23:24:52 +010034 Thrift.Configuration,
Jens Geyerd5436f52014-10-03 19:50:38 +020035 Thrift.Transport;
36
37type
38
39 TType = (
40 Stop = 0,
41 Void = 1,
42 Bool_ = 2,
43 Byte_ = 3,
44 Double_ = 4,
45 I16 = 6,
46 I32 = 8,
47 I64 = 10,
48 String_ = 11,
49 Struct = 12,
50 Map = 13,
51 Set_ = 14,
Jens Geyer62445c12022-06-29 00:00:00 +020052 List = 15,
53 Uuid = 16
Jens Geyerd5436f52014-10-03 19:50:38 +020054 );
55
56 TMessageType = (
57 Call = 1,
58 Reply = 2,
59 Exception = 3,
60 Oneway = 4
61 );
62
Jens Geyerf0e63312015-03-01 18:47:49 +010063const
64 VALID_TTYPES = [
65 TType.Stop, TType.Void,
Jens Geyer62445c12022-06-29 00:00:00 +020066 TType.Bool_, TType.Byte_, TType.Double_, TType.I16, TType.I32, TType.I64, TType.String_, TType.Uuid,
Jens Geyerf0e63312015-03-01 18:47:49 +010067 TType.Struct, TType.Map, TType.Set_, TType.List
68 ];
69
70 VALID_MESSAGETYPES = [Low(TMessageType)..High(TMessageType)];
71
72type
Jens Geyerd5436f52014-10-03 19:50:38 +020073 IProtocol = interface;
Jens Geyer17c3ad92017-09-05 20:31:27 +020074
75 TThriftMessage = record
76 Name: string;
77 Type_: TMessageType;
78 SeqID: Integer;
79 end;
80
81 TThriftStruct = record
82 Name: string;
83 end;
84
85 TThriftField = record
86 Name: string;
87 Type_: TType;
88 Id: SmallInt;
89 end;
90
91 TThriftList = record
92 ElementType: TType;
93 Count: Integer;
94 end;
95
96 TThriftMap = record
97 KeyType: TType;
98 ValueType: TType;
99 Count: Integer;
100 end;
101
102 TThriftSet = record
103 ElementType: TType;
104 Count: Integer;
105 end;
106
107
Jens Geyerd5436f52014-10-03 19:50:38 +0200108 IProtocolFactory = interface
109 ['{7CD64A10-4E9F-4E99-93BF-708A31F4A67B}']
110 function GetProtocol( const trans: ITransport): IProtocol;
111 end;
112
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100113 TProtocolException = class abstract( TException)
Jens Geyerd5436f52014-10-03 19:50:38 +0200114 public
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100115 type TExceptionType = (
116 UNKNOWN = 0,
117 INVALID_DATA = 1,
118 NEGATIVE_SIZE = 2,
119 SIZE_LIMIT = 3,
120 BAD_VERSION = 4,
121 NOT_IMPLEMENTED = 5,
122 DEPTH_LIMIT = 6
123 );
Jens Geyerfad7fd32019-11-09 23:24:52 +0100124 strict protected
Jens Geyere0e32402016-04-20 21:50:48 +0200125 constructor HiddenCreate(const Msg: string);
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100126 class function GetType: TExceptionType; virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200127 public
Jens Geyere0e32402016-04-20 21:50:48 +0200128 // purposefully hide inherited constructor
129 class function Create(const Msg: string): TProtocolException; overload; deprecated 'Use specialized TProtocolException types (or regenerate from IDL)';
130 class function Create: TProtocolException; overload; deprecated 'Use specialized TProtocolException types (or regenerate from IDL)';
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100131 class function Create( aType: TExceptionType): TProtocolException; overload; deprecated 'Use specialized TProtocolException types (or regenerate from IDL)';
132 class function Create( aType: TExceptionType; const msg: string): TProtocolException; overload; deprecated 'Use specialized TProtocolException types (or regenerate from IDL)';
133 property Type_: TExceptionType read GetType;
Jens Geyerd5436f52014-10-03 19:50:38 +0200134 end;
135
Jens Geyere0e32402016-04-20 21:50:48 +0200136 // Needed to remove deprecation warning
137 TProtocolExceptionSpecialized = class abstract (TProtocolException)
138 public
139 constructor Create(const Msg: string);
140 end;
141
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100142 TProtocolExceptionUnknown = class (TProtocolExceptionSpecialized)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100143 strict protected
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100144 class function GetType: TProtocolException.TExceptionType; override;
145 end;
146
147 TProtocolExceptionInvalidData = class (TProtocolExceptionSpecialized)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100148 strict protected
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100149 class function GetType: TProtocolException.TExceptionType; override;
150 end;
151
152 TProtocolExceptionNegativeSize = class (TProtocolExceptionSpecialized)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100153 strict protected
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100154 class function GetType: TProtocolException.TExceptionType; override;
155 end;
156
157 TProtocolExceptionSizeLimit = class (TProtocolExceptionSpecialized)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100158 strict protected
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100159 class function GetType: TProtocolException.TExceptionType; override;
160 end;
161
162 TProtocolExceptionBadVersion = class (TProtocolExceptionSpecialized)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100163 strict protected
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100164 class function GetType: TProtocolException.TExceptionType; override;
165 end;
166
167 TProtocolExceptionNotImplemented = class (TProtocolExceptionSpecialized)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100168 strict protected
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100169 class function GetType: TProtocolException.TExceptionType; override;
170 end;
171
172 TProtocolExceptionDepthLimit = class (TProtocolExceptionSpecialized)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100173 strict protected
Jens Geyer9f11c1e2019-11-09 19:39:20 +0100174 class function GetType: TProtocolException.TExceptionType; override;
175 end;
176
Jens Geyere0e32402016-04-20 21:50:48 +0200177
Jens Geyerd5436f52014-10-03 19:50:38 +0200178
179 TProtocolUtil = class
180 public
181 class procedure Skip( prot: IProtocol; type_: TType);
182 end;
183
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200184 IProtocolRecursionTracker = interface
185 ['{29CA033F-BB56-49B1-9EE3-31B1E82FC7A5}']
186 // no members yet
187 end;
188
189 TProtocolRecursionTrackerImpl = class abstract( TInterfacedObject, IProtocolRecursionTracker)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100190 strict protected
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200191 FProtocol : IProtocol;
192 public
193 constructor Create( prot : IProtocol);
194 destructor Destroy; override;
195 end;
196
Jens Geyer07f4bb52022-09-03 14:50:06 +0200197 IThriftBytes = interface; // forward
198
Jens Geyerd5436f52014-10-03 19:50:38 +0200199 IProtocol = interface
Jens Geyer07f4bb52022-09-03 14:50:06 +0200200 ['{6067A28E-15BF-4C9D-9A6F-D991BB3DCB85}']
Jens Geyerd5436f52014-10-03 19:50:38 +0200201 function GetTransport: ITransport;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200202 procedure WriteMessageBegin( const msg: TThriftMessage);
Jens Geyerd5436f52014-10-03 19:50:38 +0200203 procedure WriteMessageEnd;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200204 procedure WriteStructBegin( const struc: TThriftStruct);
Jens Geyerd5436f52014-10-03 19:50:38 +0200205 procedure WriteStructEnd;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200206 procedure WriteFieldBegin( const field: TThriftField);
Jens Geyerd5436f52014-10-03 19:50:38 +0200207 procedure WriteFieldEnd;
208 procedure WriteFieldStop;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200209 procedure WriteMapBegin( const map: TThriftMap);
Jens Geyerd5436f52014-10-03 19:50:38 +0200210 procedure WriteMapEnd;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200211 procedure WriteListBegin( const list: TThriftList);
Jens Geyerd5436f52014-10-03 19:50:38 +0200212 procedure WriteListEnd();
Jens Geyer17c3ad92017-09-05 20:31:27 +0200213 procedure WriteSetBegin( const set_: TThriftSet );
Jens Geyerd5436f52014-10-03 19:50:38 +0200214 procedure WriteSetEnd();
215 procedure WriteBool( b: Boolean);
216 procedure WriteByte( b: ShortInt);
217 procedure WriteI16( i16: SmallInt);
218 procedure WriteI32( i32: Integer);
219 procedure WriteI64( const i64: Int64);
220 procedure WriteDouble( const d: Double);
221 procedure WriteString( const s: string );
222 procedure WriteAnsiString( const s: AnsiString);
Jens Geyer07f4bb52022-09-03 14:50:06 +0200223 procedure WriteBinary( const b: TBytes); overload;
224 procedure WriteBinary( const b: IThriftBytes); overload;
Jens Geyer62445c12022-06-29 00:00:00 +0200225 procedure WriteUuid( const uuid: TGuid);
Jens Geyerd5436f52014-10-03 19:50:38 +0200226
Jens Geyer17c3ad92017-09-05 20:31:27 +0200227 function ReadMessageBegin: TThriftMessage;
Jens Geyerd5436f52014-10-03 19:50:38 +0200228 procedure ReadMessageEnd();
Jens Geyer17c3ad92017-09-05 20:31:27 +0200229 function ReadStructBegin: TThriftStruct;
Jens Geyerd5436f52014-10-03 19:50:38 +0200230 procedure ReadStructEnd;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200231 function ReadFieldBegin: TThriftField;
Jens Geyerd5436f52014-10-03 19:50:38 +0200232 procedure ReadFieldEnd();
Jens Geyer17c3ad92017-09-05 20:31:27 +0200233 function ReadMapBegin: TThriftMap;
Jens Geyerd5436f52014-10-03 19:50:38 +0200234 procedure ReadMapEnd();
Jens Geyer17c3ad92017-09-05 20:31:27 +0200235 function ReadListBegin: TThriftList;
Jens Geyerd5436f52014-10-03 19:50:38 +0200236 procedure ReadListEnd();
Jens Geyer17c3ad92017-09-05 20:31:27 +0200237 function ReadSetBegin: TThriftSet;
Jens Geyerd5436f52014-10-03 19:50:38 +0200238 procedure ReadSetEnd();
239 function ReadBool: Boolean;
240 function ReadByte: ShortInt;
241 function ReadI16: SmallInt;
242 function ReadI32: Integer;
243 function ReadI64: Int64;
244 function ReadDouble:Double;
Jens Geyer07f4bb52022-09-03 14:50:06 +0200245 function ReadBinary: TBytes; // IMPORTANT: this is NOT safe across module boundaries
246 function ReadBinaryCOM : IThriftBytes;
Jens Geyer62445c12022-06-29 00:00:00 +0200247 function ReadUuid: TGuid;
Jens Geyerd5436f52014-10-03 19:50:38 +0200248 function ReadString: string;
249 function ReadAnsiString: AnsiString;
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200250
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200251 function NextRecursionLevel : IProtocolRecursionTracker;
252 procedure IncrementRecursionDepth;
253 procedure DecrementRecursionDepth;
Jens Geyer41f47af2019-11-09 23:24:52 +0100254 function GetMinSerializedSize( const aType : TType) : Integer;
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200255
Jens Geyerd5436f52014-10-03 19:50:38 +0200256 property Transport: ITransport read GetTransport;
Jens Geyera019cda2019-11-09 23:24:52 +0100257 function Configuration : IThriftConfiguration;
Jens Geyerd5436f52014-10-03 19:50:38 +0200258 end;
259
Jens Geyer3b686532021-07-01 23:04:08 +0200260 TProtocolImplClass = class of TProtocolImpl;
261
Jens Geyerd5436f52014-10-03 19:50:38 +0200262 TProtocolImpl = class abstract( TInterfacedObject, IProtocol)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100263 strict protected
Jens Geyerd5436f52014-10-03 19:50:38 +0200264 FTrans : ITransport;
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200265 FRecursionLimit : Integer;
266 FRecursionDepth : Integer;
267
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200268 function NextRecursionLevel : IProtocolRecursionTracker;
269 procedure IncrementRecursionDepth;
270 procedure DecrementRecursionDepth;
271
Jens Geyer41f47af2019-11-09 23:24:52 +0100272 function GetMinSerializedSize( const aType : TType) : Integer; virtual; abstract;
273 procedure CheckReadBytesAvailable( const value : TThriftList); overload; inline;
274 procedure CheckReadBytesAvailable( const value : TThriftSet); overload; inline;
275 procedure CheckReadBytesAvailable( const value : TThriftMap); overload; inline;
276
277 procedure Reset; virtual;
Jens Geyera019cda2019-11-09 23:24:52 +0100278 function GetTransport: ITransport;
279 function Configuration : IThriftConfiguration;
280
Jens Geyer17c3ad92017-09-05 20:31:27 +0200281 procedure WriteMessageBegin( const msg: TThriftMessage); virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200282 procedure WriteMessageEnd; virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200283 procedure WriteStructBegin( const struc: TThriftStruct); virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200284 procedure WriteStructEnd; virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200285 procedure WriteFieldBegin( const field: TThriftField); virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200286 procedure WriteFieldEnd; virtual; abstract;
287 procedure WriteFieldStop; virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200288 procedure WriteMapBegin( const map: TThriftMap); virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200289 procedure WriteMapEnd; virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200290 procedure WriteListBegin( const list: TThriftList); virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200291 procedure WriteListEnd(); virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200292 procedure WriteSetBegin( const set_: TThriftSet ); virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200293 procedure WriteSetEnd(); virtual; abstract;
294 procedure WriteBool( b: Boolean); virtual; abstract;
295 procedure WriteByte( b: ShortInt); virtual; abstract;
296 procedure WriteI16( i16: SmallInt); virtual; abstract;
297 procedure WriteI32( i32: Integer); virtual; abstract;
298 procedure WriteI64( const i64: Int64); virtual; abstract;
299 procedure WriteDouble( const d: Double); virtual; abstract;
300 procedure WriteString( const s: string ); virtual;
301 procedure WriteAnsiString( const s: AnsiString); virtual;
Jens Geyer07f4bb52022-09-03 14:50:06 +0200302 procedure WriteBinary( const b: TBytes); overload; virtual; abstract;
Jens Geyer62445c12022-06-29 00:00:00 +0200303 procedure WriteUuid( const b: TGuid); virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200304
Jens Geyer17c3ad92017-09-05 20:31:27 +0200305 function ReadMessageBegin: TThriftMessage; virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200306 procedure ReadMessageEnd(); virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200307 function ReadStructBegin: TThriftStruct; virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200308 procedure ReadStructEnd; virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200309 function ReadFieldBegin: TThriftField; virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200310 procedure ReadFieldEnd(); virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200311 function ReadMapBegin: TThriftMap; virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200312 procedure ReadMapEnd(); virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200313 function ReadListBegin: TThriftList; virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200314 procedure ReadListEnd(); virtual; abstract;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200315 function ReadSetBegin: TThriftSet; virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200316 procedure ReadSetEnd(); virtual; abstract;
317 function ReadBool: Boolean; virtual; abstract;
318 function ReadByte: ShortInt; virtual; abstract;
319 function ReadI16: SmallInt; virtual; abstract;
320 function ReadI32: Integer; virtual; abstract;
321 function ReadI64: Int64; virtual; abstract;
322 function ReadDouble:Double; virtual; abstract;
323 function ReadBinary: TBytes; virtual; abstract;
Jens Geyer62445c12022-06-29 00:00:00 +0200324 function ReadUuid: TGuid; virtual; abstract;
Jens Geyerd5436f52014-10-03 19:50:38 +0200325 function ReadString: string; virtual;
326 function ReadAnsiString: AnsiString; virtual;
327
Jens Geyer07f4bb52022-09-03 14:50:06 +0200328 // provide generic implementation for all derived classes
329 procedure WriteBinary( const bytes : IThriftBytes); overload; virtual;
330 function ReadBinaryCOM : IThriftBytes; virtual;
331
Jens Geyera019cda2019-11-09 23:24:52 +0100332 property Transport: ITransport read GetTransport;
Jens Geyerd5436f52014-10-03 19:50:38 +0200333
Jens Geyera019cda2019-11-09 23:24:52 +0100334 public
Jens Geyer3b686532021-07-01 23:04:08 +0200335 constructor Create( const aTransport : ITransport); virtual;
Jens Geyerd5436f52014-10-03 19:50:38 +0200336 end;
337
Jens Geyer8f7487e2019-05-09 22:21:32 +0200338 IBase = interface( ISupportsToString)
339 ['{AFF6CECA-5200-4540-950E-9B89E0C1C00C}']
Jens Geyer07f4bb52022-09-03 14:50:06 +0200340 procedure Read( const prot: IProtocol);
341 procedure Write( const prot: IProtocol);
342 end;
343
344
345 IThriftBytes = interface( ISupportsToString)
346 ['{CDBEF7E8-BEF2-4A0A-983A-F334E3FF0016}']
347 function GetCount : Integer;
348 procedure SetCount(const value : Integer);
349
350 // WARNING: This returns a direct pointer to the underlying data structure
351 function QueryRawDataPtr : Pointer;
352
353 property Count : Integer read GetCount write SetCount;
354 end;
355
356
357 TThriftBytesImpl = class( TInterfacedObject, IThriftBytes, ISupportsToString)
358 strict private
359 FData : TBytes;
360
361 strict protected
362 function GetCount : Integer;
363 procedure SetCount(const value : Integer);
364 function QueryRawDataPtr : Pointer;
365
366 public
367 constructor Create; overload;
368 constructor Create( const bytes : TBytes); overload;
369 constructor Create( var bytes : TBytes; const aTakeOwnership : Boolean = FALSE); overload;
370
371 function ToString : string; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200372 end;
373
Jens Geyerd5436f52014-10-03 19:50:38 +0200374
375 TBinaryProtocolImpl = class( TProtocolImpl )
Jens Geyerfad7fd32019-11-09 23:24:52 +0100376 strict protected
Jens Geyerd5436f52014-10-03 19:50:38 +0200377 const
378 VERSION_MASK : Cardinal = $ffff0000;
379 VERSION_1 : Cardinal = $80010000;
Jens Geyerfad7fd32019-11-09 23:24:52 +0100380 strict protected
Jens Geyerd5436f52014-10-03 19:50:38 +0200381 FStrictRead : Boolean;
382 FStrictWrite : Boolean;
Jens Geyer41f47af2019-11-09 23:24:52 +0100383 function GetMinSerializedSize( const aType : TType) : Integer; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200384
Jens Geyerfad7fd32019-11-09 23:24:52 +0100385 strict private
Jens Geyer17c3ad92017-09-05 20:31:27 +0200386 function ReadAll( const pBuf : Pointer; const buflen : Integer; off: Integer; len: Integer ): Integer; inline;
Jens Geyerd5436f52014-10-03 19:50:38 +0200387 function ReadStringBody( size: Integer): string;
388
389 public
Jens Geyerd5436f52014-10-03 19:50:38 +0200390 type
391 TFactory = class( TInterfacedObject, IProtocolFactory)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100392 strict protected
Jens Geyerd5436f52014-10-03 19:50:38 +0200393 FStrictRead : Boolean;
394 FStrictWrite : Boolean;
Jens Geyerd5436f52014-10-03 19:50:38 +0200395 function GetProtocol( const trans: ITransport): IProtocol;
Jens Geyerfad7fd32019-11-09 23:24:52 +0100396 public
397 constructor Create( const aStrictRead : Boolean = FALSE; const aStrictWrite: Boolean = TRUE); reintroduce;
Jens Geyerd5436f52014-10-03 19:50:38 +0200398 end;
399
Jens Geyer3b686532021-07-01 23:04:08 +0200400 constructor Create( const trans: ITransport); overload; override;
401 constructor Create( const trans: ITransport; strictRead, strictWrite: Boolean); reintroduce; overload;
Jens Geyerd5436f52014-10-03 19:50:38 +0200402
Jens Geyer17c3ad92017-09-05 20:31:27 +0200403 procedure WriteMessageBegin( const msg: TThriftMessage); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200404 procedure WriteMessageEnd; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200405 procedure WriteStructBegin( const struc: TThriftStruct); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200406 procedure WriteStructEnd; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200407 procedure WriteFieldBegin( const field: TThriftField); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200408 procedure WriteFieldEnd; override;
409 procedure WriteFieldStop; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200410 procedure WriteMapBegin( const map: TThriftMap); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200411 procedure WriteMapEnd; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200412 procedure WriteListBegin( const list: TThriftList); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200413 procedure WriteListEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200414 procedure WriteSetBegin( const set_: TThriftSet ); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200415 procedure WriteSetEnd(); override;
416 procedure WriteBool( b: Boolean); override;
417 procedure WriteByte( b: ShortInt); override;
418 procedure WriteI16( i16: SmallInt); override;
419 procedure WriteI32( i32: Integer); override;
420 procedure WriteI64( const i64: Int64); override;
421 procedure WriteDouble( const d: Double); override;
422 procedure WriteBinary( const b: TBytes); override;
Jens Geyer62445c12022-06-29 00:00:00 +0200423 procedure WriteUuid( const uuid: TGuid); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200424
Jens Geyer17c3ad92017-09-05 20:31:27 +0200425 function ReadMessageBegin: TThriftMessage; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200426 procedure ReadMessageEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200427 function ReadStructBegin: TThriftStruct; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200428 procedure ReadStructEnd; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200429 function ReadFieldBegin: TThriftField; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200430 procedure ReadFieldEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200431 function ReadMapBegin: TThriftMap; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200432 procedure ReadMapEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200433 function ReadListBegin: TThriftList; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200434 procedure ReadListEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200435 function ReadSetBegin: TThriftSet; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200436 procedure ReadSetEnd(); override;
437 function ReadBool: Boolean; override;
438 function ReadByte: ShortInt; override;
439 function ReadI16: SmallInt; override;
440 function ReadI32: Integer; override;
441 function ReadI64: Int64; override;
442 function ReadDouble:Double; override;
443 function ReadBinary: TBytes; override;
Jens Geyer62445c12022-06-29 00:00:00 +0200444 function ReadUuid: TGuid; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200445
446 end;
447
448
449 { TProtocolDecorator forwards all requests to an enclosed TProtocol instance,
450 providing a way to author concise concrete decorator subclasses. The decorator
451 does not (and should not) modify the behaviour of the enclosed TProtocol
452
453 See p.175 of Design Patterns (by Gamma et al.)
454 }
455 TProtocolDecorator = class( TProtocolImpl)
Jens Geyerfad7fd32019-11-09 23:24:52 +0100456 strict private
Jens Geyerd5436f52014-10-03 19:50:38 +0200457 FWrappedProtocol : IProtocol;
458
Jens Geyer41f47af2019-11-09 23:24:52 +0100459 strict protected
460 function GetMinSerializedSize( const aType : TType) : Integer; override;
461
Jens Geyerd5436f52014-10-03 19:50:38 +0200462 public
463 // Encloses the specified protocol.
464 // All operations will be forward to the given protocol. Must be non-null.
Jens Geyer3b686532021-07-01 23:04:08 +0200465 constructor Create( const aProtocol : IProtocol); reintroduce;
Jens Geyerd5436f52014-10-03 19:50:38 +0200466
Jens Geyer17c3ad92017-09-05 20:31:27 +0200467 procedure WriteMessageBegin( const msg: TThriftMessage); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200468 procedure WriteMessageEnd; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200469 procedure WriteStructBegin( const struc: TThriftStruct); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200470 procedure WriteStructEnd; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200471 procedure WriteFieldBegin( const field: TThriftField); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200472 procedure WriteFieldEnd; override;
473 procedure WriteFieldStop; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200474 procedure WriteMapBegin( const map: TThriftMap); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200475 procedure WriteMapEnd; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200476 procedure WriteListBegin( const list: TThriftList); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200477 procedure WriteListEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200478 procedure WriteSetBegin( const set_: TThriftSet ); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200479 procedure WriteSetEnd(); override;
480 procedure WriteBool( b: Boolean); override;
481 procedure WriteByte( b: ShortInt); override;
482 procedure WriteI16( i16: SmallInt); override;
483 procedure WriteI32( i32: Integer); override;
484 procedure WriteI64( const i64: Int64); override;
485 procedure WriteDouble( const d: Double); override;
486 procedure WriteString( const s: string ); override;
487 procedure WriteAnsiString( const s: AnsiString); override;
488 procedure WriteBinary( const b: TBytes); override;
Jens Geyer62445c12022-06-29 00:00:00 +0200489 procedure WriteUuid( const uuid: TGuid); override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200490
Jens Geyer17c3ad92017-09-05 20:31:27 +0200491 function ReadMessageBegin: TThriftMessage; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200492 procedure ReadMessageEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200493 function ReadStructBegin: TThriftStruct; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200494 procedure ReadStructEnd; override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200495 function ReadFieldBegin: TThriftField; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200496 procedure ReadFieldEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200497 function ReadMapBegin: TThriftMap; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200498 procedure ReadMapEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200499 function ReadListBegin: TThriftList; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200500 procedure ReadListEnd(); override;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200501 function ReadSetBegin: TThriftSet; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200502 procedure ReadSetEnd(); override;
503 function ReadBool: Boolean; override;
504 function ReadByte: ShortInt; override;
505 function ReadI16: SmallInt; override;
506 function ReadI32: Integer; override;
507 function ReadI64: Int64; override;
508 function ReadDouble:Double; override;
509 function ReadBinary: TBytes; override;
Jens Geyer62445c12022-06-29 00:00:00 +0200510 function ReadUuid: TGuid; override;
Jens Geyerd5436f52014-10-03 19:50:38 +0200511 function ReadString: string; override;
512 function ReadAnsiString: AnsiString; override;
513 end;
514
515
516type
517 IRequestEvents = interface
Jens Geyer01640402013-09-25 21:12:21 +0200518 ['{F926A26A-5B00-4560-86FA-2CAE3BA73DAF}']
519 // Called before reading arguments.
520 procedure PreRead;
521 // Called between reading arguments and calling the handler.
522 procedure PostRead;
523 // Called between calling the handler and writing the response.
524 procedure PreWrite;
525 // Called after writing the response.
526 procedure PostWrite;
527 // Called when an oneway (async) function call completes successfully.
528 procedure OnewayComplete;
529 // Called if the handler throws an undeclared exception.
530 procedure UnhandledError( const e : Exception);
531 // Called when a client has finished request-handling to clean up
532 procedure CleanupContext;
533 end;
534
535
536 IProcessorEvents = interface
537 ['{A8661119-657C-447D-93C5-512E36162A45}']
538 // Called when a client is about to call the processor.
539 procedure Processing( const transport : ITransport);
540 // Called on any service function invocation
541 function CreateRequestContext( const aFunctionName : string) : IRequestEvents;
542 // Called when a client has finished request-handling to clean up
543 procedure CleanupContext;
544 end;
545
546
547 IProcessor = interface
548 ['{7BAE92A5-46DA-4F13-B6EA-0EABE233EE5F}']
Jens Geyerd430bbd2013-09-26 23:37:54 +0200549 function Process( const iprot :IProtocol; const oprot: IProtocol; const events : IProcessorEvents = nil): Boolean;
Jens Geyer01640402013-09-25 21:12:21 +0200550 end;
551
Jens Geyerd5436f52014-10-03 19:50:38 +0200552
Jens Geyer17c3ad92017-09-05 20:31:27 +0200553procedure Init( var rec : TThriftMessage; const AName: string = ''; const AMessageType: TMessageType = Low(TMessageType); const ASeqID: Integer = 0); overload; inline;
554procedure Init( var rec : TThriftStruct; const AName: string = ''); overload; inline;
555procedure Init( var rec : TThriftField; const AName: string = ''; const AType: TType = Low(TType); const AID: SmallInt = 0); overload; inline;
556procedure Init( var rec : TThriftMap; const AKeyType: TType = Low(TType); const AValueType: TType = Low(TType); const ACount: Integer = 0); overload; inline;
557procedure Init( var rec : TThriftSet; const AElementType: TType = Low(TType); const ACount: Integer = 0); overload; inline;
558procedure Init( var rec : TThriftList; const AElementType: TType = Low(TType); const ACount: Integer = 0); overload; inline;
559
Jens Geyerd5436f52014-10-03 19:50:38 +0200560
561implementation
562
Jens Geyerfad7fd32019-11-09 23:24:52 +0100563function ConvertInt64ToDouble( const n: Int64): Double; inline;
Jens Geyerd5436f52014-10-03 19:50:38 +0200564begin
565 ASSERT( SizeOf(n) = SizeOf(Result));
566 System.Move( n, Result, SizeOf(Result));
567end;
568
Jens Geyerfad7fd32019-11-09 23:24:52 +0100569function ConvertDoubleToInt64( const d: Double): Int64; inline;
Jens Geyerd5436f52014-10-03 19:50:38 +0200570begin
571 ASSERT( SizeOf(d) = SizeOf(Result));
572 System.Move( d, Result, SizeOf(Result));
573end;
574
Jens Geyerd5436f52014-10-03 19:50:38 +0200575
Jens Geyerd5436f52014-10-03 19:50:38 +0200576
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200577{ TProtocolRecursionTrackerImpl }
578
579constructor TProtocolRecursionTrackerImpl.Create( prot : IProtocol);
580begin
581 inherited Create;
582
583 // storing the pointer *after* the (successful) increment is important here
584 prot.IncrementRecursionDepth;
585 FProtocol := prot;
586end;
587
588destructor TProtocolRecursionTrackerImpl.Destroy;
589begin
590 try
591 // we have to release the reference iff the pointer has been stored
592 if FProtocol <> nil then begin
593 FProtocol.DecrementRecursionDepth;
594 FProtocol := nil;
595 end;
596 finally
597 inherited Destroy;
598 end;
599end;
600
Jens Geyerd5436f52014-10-03 19:50:38 +0200601{ TProtocolImpl }
602
Jens Geyera019cda2019-11-09 23:24:52 +0100603constructor TProtocolImpl.Create( const aTransport : ITransport);
Jens Geyerd5436f52014-10-03 19:50:38 +0200604begin
605 inherited Create;
Jens Geyera019cda2019-11-09 23:24:52 +0100606 FTrans := aTransport;
607 FRecursionLimit := aTransport.Configuration.RecursionLimit;
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200608 FRecursionDepth := 0;
609end;
610
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200611function TProtocolImpl.NextRecursionLevel : IProtocolRecursionTracker;
612begin
613 result := TProtocolRecursionTrackerImpl.Create(Self);
614end;
615
616procedure TProtocolImpl.IncrementRecursionDepth;
617begin
618 if FRecursionDepth < FRecursionLimit
619 then Inc(FRecursionDepth)
Jens Geyere0e32402016-04-20 21:50:48 +0200620 else raise TProtocolExceptionDepthLimit.Create('Depth limit exceeded');
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200621end;
622
623procedure TProtocolImpl.DecrementRecursionDepth;
624begin
625 Dec(FRecursionDepth)
Jens Geyerd5436f52014-10-03 19:50:38 +0200626end;
627
628function TProtocolImpl.GetTransport: ITransport;
629begin
630 Result := FTrans;
631end;
632
Jens Geyera019cda2019-11-09 23:24:52 +0100633function TProtocolImpl.Configuration : IThriftConfiguration;
634begin
635 Result := FTrans.Configuration;
636end;
637
Jens Geyer41f47af2019-11-09 23:24:52 +0100638procedure TProtocolImpl.Reset;
639begin
Jens Geyera019cda2019-11-09 23:24:52 +0100640 FTrans.ResetConsumedMessageSize;
Jens Geyer41f47af2019-11-09 23:24:52 +0100641end;
642
Jens Geyerd5436f52014-10-03 19:50:38 +0200643function TProtocolImpl.ReadAnsiString: AnsiString;
644var
645 b : TBytes;
646 len : Integer;
647begin
648 Result := '';
649 b := ReadBinary;
650 len := Length( b );
Jens Geyerfad7fd32019-11-09 23:24:52 +0100651 if len > 0 then begin
Jens Geyerd5436f52014-10-03 19:50:38 +0200652 SetLength( Result, len);
653 System.Move( b[0], Pointer(Result)^, len );
654 end;
655end;
656
657function TProtocolImpl.ReadString: string;
658begin
659 Result := TEncoding.UTF8.GetString( ReadBinary );
660end;
661
662procedure TProtocolImpl.WriteAnsiString(const s: AnsiString);
663var
664 b : TBytes;
665 len : Integer;
666begin
667 len := Length(s);
668 SetLength( b, len);
Jens Geyerfad7fd32019-11-09 23:24:52 +0100669 if len > 0 then begin
Jens Geyerd5436f52014-10-03 19:50:38 +0200670 System.Move( Pointer(s)^, b[0], len );
671 end;
672 WriteBinary( b );
673end;
674
675procedure TProtocolImpl.WriteString(const s: string);
676var
677 b : TBytes;
678begin
679 b := TEncoding.UTF8.GetBytes(s);
680 WriteBinary( b );
681end;
682
Jens Geyer41f47af2019-11-09 23:24:52 +0100683
684procedure TProtocolImpl.CheckReadBytesAvailable( const value : TThriftList);
685begin
686 FTrans.CheckReadBytesAvailable( value.Count * GetMinSerializedSize(value.ElementType));
687end;
688
689
690procedure TProtocolImpl.CheckReadBytesAvailable( const value : TThriftSet);
691begin
692 FTrans.CheckReadBytesAvailable( value.Count * GetMinSerializedSize(value.ElementType));
693end;
694
695
696procedure TProtocolImpl.CheckReadBytesAvailable( const value : TThriftMap);
Jens Geyera019cda2019-11-09 23:24:52 +0100697var nPairSize : Integer;
Jens Geyer41f47af2019-11-09 23:24:52 +0100698begin
699 nPairSize := GetMinSerializedSize(value.KeyType) + GetMinSerializedSize(value.ValueType);
700 FTrans.CheckReadBytesAvailable( value.Count * nPairSize);
701end;
702
Jens Geyer07f4bb52022-09-03 14:50:06 +0200703
704procedure TProtocolImpl.WriteBinary( const bytes : IThriftBytes);
705var tmp : TBytes;
706begin
707 SetLength( tmp, bytes.Count);
708 if Length(tmp) > 0
709 then Move( bytes.QueryRawDataPtr^, tmp[0], Length(tmp));
710 WriteBinary( tmp);
711end;
712
713
714function TProtocolImpl.ReadBinaryCOM : IThriftBytes;
715var bytes : TBytes;
716begin
717 bytes := ReadBinary;
718 result := TThriftBytesImpl.Create(bytes,TRUE);
719end;
720
721
722{ TThriftBytesImpl }
723
724constructor TThriftBytesImpl.Create;
725begin
726 inherited Create;
727 ASSERT( Length(FData) = 0);
728end;
729
730
731constructor TThriftBytesImpl.Create( const bytes : TBytes);
732begin
733 FData := bytes; // copies the data
734end;
735
736
737constructor TThriftBytesImpl.Create( var bytes : TBytes; const aTakeOwnership : Boolean);
738
739 procedure SwapPointer( var one, two);
740 var
741 pOne : Pointer absolute one;
742 pTwo : Pointer absolute two;
743 pTmp : Pointer;
744 begin
745 pTmp := pOne;
746 pOne := pTwo;
747 pTwo := pTmp;
748 end;
749
750begin
751 inherited Create;
752 ASSERT( Length(FData) = 0);
753
754 if aTakeOwnership
755 then SwapPointer( FData, bytes)
756 else FData := bytes; // copies the data
757end;
758
759
760function TThriftBytesImpl.ToString : string;
761var sb : TThriftStringBuilder;
762begin
763 sb := TThriftStringBuilder.Create();
764 try
765 sb.Append('Bin: ');
766 sb.Append( FData);
767
768 result := sb.ToString;
769 finally
770 sb.Free;
771 end;
772end;
773
774
775function TThriftBytesImpl.GetCount : Integer;
776begin
777 result := Length(FData);
778end;
779
780
781procedure TThriftBytesImpl.SetCount(const value : Integer);
782begin
783 SetLength( FData, value);
784end;
785
786
787function TThriftBytesImpl.QueryRawDataPtr : Pointer;
788begin
789 result := FData;
790end;
791
Jens Geyerd5436f52014-10-03 19:50:38 +0200792{ TProtocolUtil }
793
794class procedure TProtocolUtil.Skip( prot: IProtocol; type_: TType);
Jens Geyer17c3ad92017-09-05 20:31:27 +0200795var field : TThriftField;
796 map : TThriftMap;
797 set_ : TThriftSet;
798 list : TThriftList;
Jens Geyerd5436f52014-10-03 19:50:38 +0200799 i : Integer;
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200800 tracker : IProtocolRecursionTracker;
Jens Geyerd5436f52014-10-03 19:50:38 +0200801begin
Jens Geyerd47fcdd2015-07-09 22:05:18 +0200802 tracker := prot.NextRecursionLevel;
Jens Geyerd5436f52014-10-03 19:50:38 +0200803 case type_ of
804 // simple types
805 TType.Bool_ : prot.ReadBool();
806 TType.Byte_ : prot.ReadByte();
807 TType.I16 : prot.ReadI16();
808 TType.I32 : prot.ReadI32();
809 TType.I64 : prot.ReadI64();
810 TType.Double_ : prot.ReadDouble();
811 TType.String_ : prot.ReadBinary();// Don't try to decode the string, just skip it.
Jens Geyer62445c12022-06-29 00:00:00 +0200812 TType.Uuid : prot.ReadUuid();
Jens Geyerd5436f52014-10-03 19:50:38 +0200813
814 // structured types
815 TType.Struct : begin
816 prot.ReadStructBegin();
817 while TRUE do begin
818 field := prot.ReadFieldBegin();
819 if (field.Type_ = TType.Stop) then Break;
820 Skip(prot, field.Type_);
821 prot.ReadFieldEnd();
822 end;
823 prot.ReadStructEnd();
824 end;
825
826 TType.Map : begin
827 map := prot.ReadMapBegin();
828 for i := 0 to map.Count-1 do begin
829 Skip(prot, map.KeyType);
830 Skip(prot, map.ValueType);
831 end;
832 prot.ReadMapEnd();
833 end;
834
835 TType.Set_ : begin
836 set_ := prot.ReadSetBegin();
837 for i := 0 to set_.Count-1
838 do Skip( prot, set_.ElementType);
839 prot.ReadSetEnd();
840 end;
841
842 TType.List : begin
843 list := prot.ReadListBegin();
844 for i := 0 to list.Count-1
845 do Skip( prot, list.ElementType);
846 prot.ReadListEnd();
847 end;
848
849 else
Jens Geyer5f723cd2017-01-10 21:57:48 +0100850 raise TProtocolExceptionInvalidData.Create('Unexpected type '+IntToStr(Ord(type_)));
Jens Geyerd5436f52014-10-03 19:50:38 +0200851 end;
852end;
853
Jens Geyerd5436f52014-10-03 19:50:38 +0200854
855{ TBinaryProtocolImpl }
856
Jens Geyer3b686532021-07-01 23:04:08 +0200857constructor TBinaryProtocolImpl.Create( const trans: ITransport);
858begin
859 // call the real CTOR
860 Self.Create( trans, FALSE, TRUE);
861end;
862
Jens Geyerfad7fd32019-11-09 23:24:52 +0100863constructor TBinaryProtocolImpl.Create( const trans: ITransport; strictRead, strictWrite: Boolean);
Jens Geyerd5436f52014-10-03 19:50:38 +0200864begin
Jens Geyerfad7fd32019-11-09 23:24:52 +0100865 inherited Create( trans);
Jens Geyerd5436f52014-10-03 19:50:38 +0200866 FStrictRead := strictRead;
867 FStrictWrite := strictWrite;
868end;
869
Jens Geyer17c3ad92017-09-05 20:31:27 +0200870function TBinaryProtocolImpl.ReadAll( const pBuf : Pointer; const buflen : Integer; off: Integer; len: Integer ): Integer;
Jens Geyerd5436f52014-10-03 19:50:38 +0200871begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200872 Result := FTrans.ReadAll( pBuf, buflen, off, len );
Jens Geyerd5436f52014-10-03 19:50:38 +0200873end;
874
875function TBinaryProtocolImpl.ReadBinary: TBytes;
876var
877 size : Integer;
878 buf : TBytes;
879begin
880 size := ReadI32;
Jens Geyer41f47af2019-11-09 23:24:52 +0100881 FTrans.CheckReadBytesAvailable( size);
Jens Geyerfad7fd32019-11-09 23:24:52 +0100882 SetLength( buf, size);
Jens Geyerd5436f52014-10-03 19:50:38 +0200883 FTrans.ReadAll( buf, 0, size);
884 Result := buf;
885end;
886
Jens Geyer62445c12022-06-29 00:00:00 +0200887function TBinaryProtocolImpl.ReadUuid : TGuid;
888var network : TGuid; // in network order (Big Endian)
889begin
890 ASSERT( SizeOf(result) = 16);
891 FTrans.ReadAll( @network, SizeOf(network), 0, SizeOf(network));
Jens Geyerf8f62782022-09-10 00:55:02 +0200892 result := GuidUtils.SwapByteOrder(network);
Jens Geyer62445c12022-06-29 00:00:00 +0200893end;
894
Jens Geyerd5436f52014-10-03 19:50:38 +0200895function TBinaryProtocolImpl.ReadBool: Boolean;
896begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200897 Result := (ReadByte = 1);
Jens Geyerd5436f52014-10-03 19:50:38 +0200898end;
899
900function TBinaryProtocolImpl.ReadByte: ShortInt;
Jens Geyerd5436f52014-10-03 19:50:38 +0200901begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200902 ReadAll( @result, SizeOf(result), 0, 1);
Jens Geyerd5436f52014-10-03 19:50:38 +0200903end;
904
905function TBinaryProtocolImpl.ReadDouble: Double;
906begin
907 Result := ConvertInt64ToDouble( ReadI64 )
908end;
909
Jens Geyer17c3ad92017-09-05 20:31:27 +0200910function TBinaryProtocolImpl.ReadFieldBegin: TThriftField;
Jens Geyerd5436f52014-10-03 19:50:38 +0200911begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200912 Init( result, '', TType( ReadByte), 0);
913 if ( result.Type_ <> TType.Stop ) then begin
914 result.Id := ReadI16;
Jens Geyerd5436f52014-10-03 19:50:38 +0200915 end;
Jens Geyerd5436f52014-10-03 19:50:38 +0200916end;
917
918procedure TBinaryProtocolImpl.ReadFieldEnd;
919begin
920
921end;
922
923function TBinaryProtocolImpl.ReadI16: SmallInt;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200924var i16in : packed array[0..1] of Byte;
Jens Geyerd5436f52014-10-03 19:50:38 +0200925begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200926 ReadAll( @i16in, Sizeof(i16in), 0, 2);
Jens Geyerd5436f52014-10-03 19:50:38 +0200927 Result := SmallInt(((i16in[0] and $FF) shl 8) or (i16in[1] and $FF));
928end;
929
930function TBinaryProtocolImpl.ReadI32: Integer;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200931var i32in : packed array[0..3] of Byte;
Jens Geyerd5436f52014-10-03 19:50:38 +0200932begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200933 ReadAll( @i32in, SizeOf(i32in), 0, 4);
Jens Geyerd5436f52014-10-03 19:50:38 +0200934
935 Result := Integer(
936 ((i32in[0] and $FF) shl 24) or
937 ((i32in[1] and $FF) shl 16) or
938 ((i32in[2] and $FF) shl 8) or
939 (i32in[3] and $FF));
940
941end;
942
943function TBinaryProtocolImpl.ReadI64: Int64;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200944var i64in : packed array[0..7] of Byte;
Jens Geyerd5436f52014-10-03 19:50:38 +0200945begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200946 ReadAll( @i64in, SizeOf(i64in), 0, 8);
Jens Geyerd5436f52014-10-03 19:50:38 +0200947 Result :=
948 (Int64( i64in[0] and $FF) shl 56) or
949 (Int64( i64in[1] and $FF) shl 48) or
950 (Int64( i64in[2] and $FF) shl 40) or
951 (Int64( i64in[3] and $FF) shl 32) or
952 (Int64( i64in[4] and $FF) shl 24) or
953 (Int64( i64in[5] and $FF) shl 16) or
954 (Int64( i64in[6] and $FF) shl 8) or
955 (Int64( i64in[7] and $FF));
956end;
957
Jens Geyer17c3ad92017-09-05 20:31:27 +0200958function TBinaryProtocolImpl.ReadListBegin: TThriftList;
Jens Geyerd5436f52014-10-03 19:50:38 +0200959begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200960 result.ElementType := TType(ReadByte);
961 result.Count := ReadI32;
Jens Geyer41f47af2019-11-09 23:24:52 +0100962 CheckReadBytesAvailable(result);
Jens Geyerd5436f52014-10-03 19:50:38 +0200963end;
964
965procedure TBinaryProtocolImpl.ReadListEnd;
966begin
967
968end;
969
Jens Geyer17c3ad92017-09-05 20:31:27 +0200970function TBinaryProtocolImpl.ReadMapBegin: TThriftMap;
Jens Geyerd5436f52014-10-03 19:50:38 +0200971begin
Jens Geyer17c3ad92017-09-05 20:31:27 +0200972 result.KeyType := TType(ReadByte);
973 result.ValueType := TType(ReadByte);
974 result.Count := ReadI32;
Jens Geyer41f47af2019-11-09 23:24:52 +0100975 CheckReadBytesAvailable(result);
Jens Geyerd5436f52014-10-03 19:50:38 +0200976end;
977
978procedure TBinaryProtocolImpl.ReadMapEnd;
979begin
980
981end;
982
Jens Geyer17c3ad92017-09-05 20:31:27 +0200983function TBinaryProtocolImpl.ReadMessageBegin: TThriftMessage;
Jens Geyerd5436f52014-10-03 19:50:38 +0200984var
985 size : Integer;
986 version : Integer;
Jens Geyerd5436f52014-10-03 19:50:38 +0200987begin
Jens Geyer41f47af2019-11-09 23:24:52 +0100988 Reset;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200989 Init( result);
Jens Geyer589ee5b2021-03-29 21:40:55 +0200990
Jens Geyerd5436f52014-10-03 19:50:38 +0200991 size := ReadI32;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200992 if (size < 0) then begin
Jens Geyerd5436f52014-10-03 19:50:38 +0200993 version := size and Integer( VERSION_MASK);
Jens Geyer17c3ad92017-09-05 20:31:27 +0200994 if ( version <> Integer( VERSION_1)) then begin
Jens Geyere0e32402016-04-20 21:50:48 +0200995 raise TProtocolExceptionBadVersion.Create('Bad version in ReadMessageBegin: ' + IntToStr(version) );
Jens Geyerd5436f52014-10-03 19:50:38 +0200996 end;
Jens Geyer17c3ad92017-09-05 20:31:27 +0200997 result.Type_ := TMessageType( size and $000000ff);
998 result.Name := ReadString;
999 result.SeqID := ReadI32;
Jens Geyer589ee5b2021-03-29 21:40:55 +02001000 Exit;
1001 end;
1002
1003 try
1004 if FStrictRead
1005 then raise TProtocolExceptionBadVersion.Create('Missing version in readMessageBegin, old client?' );
1006
Jens Geyer17c3ad92017-09-05 20:31:27 +02001007 result.Name := ReadStringBody( size );
1008 result.Type_ := TMessageType( ReadByte );
1009 result.SeqID := ReadI32;
Jens Geyer589ee5b2021-03-29 21:40:55 +02001010 except
1011 if CharUtils.IsHtmlDoctype(size)
1012 then raise TProtocolExceptionInvalidData.Create('Remote end sends HTML instead of data')
1013 else raise; // something else
Jens Geyerd5436f52014-10-03 19:50:38 +02001014 end;
Jens Geyerd5436f52014-10-03 19:50:38 +02001015end;
1016
1017procedure TBinaryProtocolImpl.ReadMessageEnd;
1018begin
1019 inherited;
1020
1021end;
1022
Jens Geyer17c3ad92017-09-05 20:31:27 +02001023function TBinaryProtocolImpl.ReadSetBegin: TThriftSet;
Jens Geyerd5436f52014-10-03 19:50:38 +02001024begin
Jens Geyer17c3ad92017-09-05 20:31:27 +02001025 result.ElementType := TType(ReadByte);
1026 result.Count := ReadI32;
Jens Geyer41f47af2019-11-09 23:24:52 +01001027 CheckReadBytesAvailable(result);
Jens Geyerd5436f52014-10-03 19:50:38 +02001028end;
1029
1030procedure TBinaryProtocolImpl.ReadSetEnd;
1031begin
1032
1033end;
1034
1035function TBinaryProtocolImpl.ReadStringBody( size: Integer): string;
Jens Geyerfad7fd32019-11-09 23:24:52 +01001036var buf : TBytes;
Jens Geyerd5436f52014-10-03 19:50:38 +02001037begin
Jens Geyer41f47af2019-11-09 23:24:52 +01001038 FTrans.CheckReadBytesAvailable( size);
Jens Geyerfad7fd32019-11-09 23:24:52 +01001039 SetLength( buf, size);
Jens Geyerd5436f52014-10-03 19:50:38 +02001040 FTrans.ReadAll( buf, 0, size );
1041 Result := TEncoding.UTF8.GetString( buf);
1042end;
1043
Jens Geyer17c3ad92017-09-05 20:31:27 +02001044function TBinaryProtocolImpl.ReadStructBegin: TThriftStruct;
Jens Geyerd5436f52014-10-03 19:50:38 +02001045begin
Jens Geyer17c3ad92017-09-05 20:31:27 +02001046 Init( Result);
Jens Geyerd5436f52014-10-03 19:50:38 +02001047end;
1048
1049procedure TBinaryProtocolImpl.ReadStructEnd;
1050begin
1051 inherited;
1052
1053end;
1054
1055procedure TBinaryProtocolImpl.WriteBinary( const b: TBytes);
1056var iLen : Integer;
1057begin
1058 iLen := Length(b);
1059 WriteI32( iLen);
1060 if iLen > 0 then FTrans.Write(b, 0, iLen);
1061end;
1062
Jens Geyer62445c12022-06-29 00:00:00 +02001063procedure TBinaryProtocolImpl.WriteUuid( const uuid: TGuid);
1064var network : TGuid; // in network order (Big Endian)
1065begin
1066 ASSERT( SizeOf(uuid) = 16);
Jens Geyerf8f62782022-09-10 00:55:02 +02001067 network := GuidUtils.SwapByteOrder(uuid);
Jens Geyer62445c12022-06-29 00:00:00 +02001068 Transport.Write( @network, 0, SizeOf(network));
1069end;
1070
Jens Geyerd5436f52014-10-03 19:50:38 +02001071procedure TBinaryProtocolImpl.WriteBool(b: Boolean);
1072begin
Jens Geyer17c3ad92017-09-05 20:31:27 +02001073 if b then begin
Jens Geyerd5436f52014-10-03 19:50:38 +02001074 WriteByte( 1 );
Jens Geyer17c3ad92017-09-05 20:31:27 +02001075 end else begin
Jens Geyerd5436f52014-10-03 19:50:38 +02001076 WriteByte( 0 );
1077 end;
1078end;
1079
1080procedure TBinaryProtocolImpl.WriteByte(b: ShortInt);
Jens Geyerd5436f52014-10-03 19:50:38 +02001081begin
Jens Geyer17c3ad92017-09-05 20:31:27 +02001082 FTrans.Write( @b, 0, 1);
Jens Geyerd5436f52014-10-03 19:50:38 +02001083end;
1084
1085procedure TBinaryProtocolImpl.WriteDouble( const d: Double);
1086begin
1087 WriteI64(ConvertDoubleToInt64(d));
1088end;
1089
Jens Geyer17c3ad92017-09-05 20:31:27 +02001090procedure TBinaryProtocolImpl.WriteFieldBegin( const field: TThriftField);
Jens Geyerd5436f52014-10-03 19:50:38 +02001091begin
1092 WriteByte(ShortInt(field.Type_));
1093 WriteI16(field.ID);
1094end;
1095
1096procedure TBinaryProtocolImpl.WriteFieldEnd;
1097begin
1098
1099end;
1100
1101procedure TBinaryProtocolImpl.WriteFieldStop;
1102begin
1103 WriteByte(ShortInt(TType.Stop));
1104end;
1105
1106procedure TBinaryProtocolImpl.WriteI16(i16: SmallInt);
Jens Geyer17c3ad92017-09-05 20:31:27 +02001107var i16out : packed array[0..1] of Byte;
Jens Geyerd5436f52014-10-03 19:50:38 +02001108begin
Jens Geyerd5436f52014-10-03 19:50:38 +02001109 i16out[0] := Byte($FF and (i16 shr 8));
1110 i16out[1] := Byte($FF and i16);
Jens Geyer17c3ad92017-09-05 20:31:27 +02001111 FTrans.Write( @i16out, 0, 2);
Jens Geyerd5436f52014-10-03 19:50:38 +02001112end;
1113
1114procedure TBinaryProtocolImpl.WriteI32(i32: Integer);
Jens Geyer17c3ad92017-09-05 20:31:27 +02001115var i32out : packed array[0..3] of Byte;
Jens Geyerd5436f52014-10-03 19:50:38 +02001116begin
Jens Geyerd5436f52014-10-03 19:50:38 +02001117 i32out[0] := Byte($FF and (i32 shr 24));
1118 i32out[1] := Byte($FF and (i32 shr 16));
1119 i32out[2] := Byte($FF and (i32 shr 8));
1120 i32out[3] := Byte($FF and i32);
Jens Geyer17c3ad92017-09-05 20:31:27 +02001121 FTrans.Write( @i32out, 0, 4);
Jens Geyerd5436f52014-10-03 19:50:38 +02001122end;
1123
1124procedure TBinaryProtocolImpl.WriteI64( const i64: Int64);
Jens Geyer17c3ad92017-09-05 20:31:27 +02001125var i64out : packed array[0..7] of Byte;
Jens Geyerd5436f52014-10-03 19:50:38 +02001126begin
Jens Geyerd5436f52014-10-03 19:50:38 +02001127 i64out[0] := Byte($FF and (i64 shr 56));
1128 i64out[1] := Byte($FF and (i64 shr 48));
1129 i64out[2] := Byte($FF and (i64 shr 40));
1130 i64out[3] := Byte($FF and (i64 shr 32));
1131 i64out[4] := Byte($FF and (i64 shr 24));
1132 i64out[5] := Byte($FF and (i64 shr 16));
1133 i64out[6] := Byte($FF and (i64 shr 8));
1134 i64out[7] := Byte($FF and i64);
Jens Geyer17c3ad92017-09-05 20:31:27 +02001135 FTrans.Write( @i64out, 0, 8);
Jens Geyerd5436f52014-10-03 19:50:38 +02001136end;
1137
Jens Geyer17c3ad92017-09-05 20:31:27 +02001138procedure TBinaryProtocolImpl.WriteListBegin( const list: TThriftList);
Jens Geyerd5436f52014-10-03 19:50:38 +02001139begin
1140 WriteByte(ShortInt(list.ElementType));
1141 WriteI32(list.Count);
1142end;
1143
1144procedure TBinaryProtocolImpl.WriteListEnd;
1145begin
1146
1147end;
1148
Jens Geyer17c3ad92017-09-05 20:31:27 +02001149procedure TBinaryProtocolImpl.WriteMapBegin( const map: TThriftMap);
Jens Geyerd5436f52014-10-03 19:50:38 +02001150begin
1151 WriteByte(ShortInt(map.KeyType));
1152 WriteByte(ShortInt(map.ValueType));
1153 WriteI32(map.Count);
1154end;
1155
1156procedure TBinaryProtocolImpl.WriteMapEnd;
1157begin
1158
1159end;
1160
Jens Geyer17c3ad92017-09-05 20:31:27 +02001161procedure TBinaryProtocolImpl.WriteMessageBegin( const msg: TThriftMessage);
Jens Geyerfad7fd32019-11-09 23:24:52 +01001162var version : Cardinal;
Jens Geyerd5436f52014-10-03 19:50:38 +02001163begin
Jens Geyer41f47af2019-11-09 23:24:52 +01001164 Reset;
Jens Geyerfad7fd32019-11-09 23:24:52 +01001165 if FStrictWrite then begin
Jens Geyerd5436f52014-10-03 19:50:38 +02001166 version := VERSION_1 or Cardinal( msg.Type_);
1167 WriteI32( Integer( version) );
1168 WriteString( msg.Name);
1169 WriteI32( msg.SeqID);
Jens Geyerfad7fd32019-11-09 23:24:52 +01001170 end else begin
Jens Geyerd5436f52014-10-03 19:50:38 +02001171 WriteString( msg.Name);
1172 WriteByte(ShortInt( msg.Type_));
1173 WriteI32( msg.SeqID);
1174 end;
1175end;
1176
1177procedure TBinaryProtocolImpl.WriteMessageEnd;
1178begin
1179
1180end;
1181
Jens Geyer17c3ad92017-09-05 20:31:27 +02001182procedure TBinaryProtocolImpl.WriteSetBegin( const set_: TThriftSet);
Jens Geyerd5436f52014-10-03 19:50:38 +02001183begin
1184 WriteByte(ShortInt(set_.ElementType));
1185 WriteI32(set_.Count);
1186end;
1187
1188procedure TBinaryProtocolImpl.WriteSetEnd;
1189begin
1190
1191end;
1192
Jens Geyer17c3ad92017-09-05 20:31:27 +02001193procedure TBinaryProtocolImpl.WriteStructBegin( const struc: TThriftStruct);
Jens Geyerd5436f52014-10-03 19:50:38 +02001194begin
1195
1196end;
1197
1198procedure TBinaryProtocolImpl.WriteStructEnd;
1199begin
1200
1201end;
1202
Jens Geyer41f47af2019-11-09 23:24:52 +01001203function TBinaryProtocolImpl.GetMinSerializedSize( const aType : TType) : Integer;
1204// Return the minimum number of bytes a type will consume on the wire
1205begin
1206 case aType of
1207 TType.Stop: result := 0;
1208 TType.Void: result := 0;
1209 TType.Bool_: result := SizeOf(Byte);
1210 TType.Byte_: result := SizeOf(Byte);
1211 TType.Double_: result := SizeOf(Double);
1212 TType.I16: result := SizeOf(Int16);
1213 TType.I32: result := SizeOf(Int32);
1214 TType.I64: result := SizeOf(Int64);
1215 TType.String_: result := SizeOf(Int32); // string length
1216 TType.Struct: result := 0; // empty struct
1217 TType.Map: result := SizeOf(Int32); // element count
1218 TType.Set_: result := SizeOf(Int32); // element count
1219 TType.List: result := SizeOf(Int32); // element count
Jens Geyer62445c12022-06-29 00:00:00 +02001220 TType.Uuid: result := SizeOf(TGuid);
Jens Geyer41f47af2019-11-09 23:24:52 +01001221 else
1222 raise TTransportExceptionBadArgs.Create('Unhandled type code');
1223 end;
1224end;
1225
1226
Jens Geyerd5436f52014-10-03 19:50:38 +02001227{ TProtocolException }
1228
Jens Geyere0e32402016-04-20 21:50:48 +02001229constructor TProtocolException.HiddenCreate(const Msg: string);
Jens Geyerd5436f52014-10-03 19:50:38 +02001230begin
Jens Geyere0e32402016-04-20 21:50:48 +02001231 inherited Create(Msg);
Jens Geyerd5436f52014-10-03 19:50:38 +02001232end;
1233
Jens Geyere0e32402016-04-20 21:50:48 +02001234class function TProtocolException.Create(const Msg: string): TProtocolException;
Jens Geyerd5436f52014-10-03 19:50:38 +02001235begin
Jens Geyere0e32402016-04-20 21:50:48 +02001236 Result := TProtocolExceptionUnknown.Create(Msg);
Jens Geyerd5436f52014-10-03 19:50:38 +02001237end;
1238
Jens Geyere0e32402016-04-20 21:50:48 +02001239class function TProtocolException.Create: TProtocolException;
Jens Geyerd5436f52014-10-03 19:50:38 +02001240begin
Jens Geyere0e32402016-04-20 21:50:48 +02001241 Result := TProtocolExceptionUnknown.Create('');
1242end;
1243
Jens Geyer9f11c1e2019-11-09 19:39:20 +01001244class function TProtocolException.Create(aType: TExceptionType): TProtocolException;
Jens Geyere0e32402016-04-20 21:50:48 +02001245begin
1246{$WARN SYMBOL_DEPRECATED OFF}
Jens Geyer9f11c1e2019-11-09 19:39:20 +01001247 Result := Create(aType, '');
Jens Geyere0e32402016-04-20 21:50:48 +02001248{$WARN SYMBOL_DEPRECATED DEFAULT}
1249end;
1250
Jens Geyer9f11c1e2019-11-09 19:39:20 +01001251class function TProtocolException.Create(aType: TExceptionType; const msg: string): TProtocolException;
Jens Geyere0e32402016-04-20 21:50:48 +02001252begin
Jens Geyer9f11c1e2019-11-09 19:39:20 +01001253 case aType of
1254 TExceptionType.INVALID_DATA: Result := TProtocolExceptionInvalidData.Create(msg);
1255 TExceptionType.NEGATIVE_SIZE: Result := TProtocolExceptionNegativeSize.Create(msg);
1256 TExceptionType.SIZE_LIMIT: Result := TProtocolExceptionSizeLimit.Create(msg);
1257 TExceptionType.BAD_VERSION: Result := TProtocolExceptionBadVersion.Create(msg);
1258 TExceptionType.NOT_IMPLEMENTED: Result := TProtocolExceptionNotImplemented.Create(msg);
1259 TExceptionType.DEPTH_LIMIT: Result := TProtocolExceptionDepthLimit.Create(msg);
Jens Geyere0e32402016-04-20 21:50:48 +02001260 else
Jens Geyer9f11c1e2019-11-09 19:39:20 +01001261 ASSERT( TExceptionType.UNKNOWN = aType);
Jens Geyere0e32402016-04-20 21:50:48 +02001262 Result := TProtocolExceptionUnknown.Create(msg);
1263 end;
1264end;
1265
1266{ TProtocolExceptionSpecialized }
1267
1268constructor TProtocolExceptionSpecialized.Create(const Msg: string);
1269begin
1270 inherited HiddenCreate(Msg);
Jens Geyerd5436f52014-10-03 19:50:38 +02001271end;
1272
Jens Geyer9f11c1e2019-11-09 19:39:20 +01001273{ specialized TProtocolExceptions }
1274
1275class function TProtocolExceptionUnknown.GetType: TProtocolException.TExceptionType;
1276begin
1277 result := TExceptionType.UNKNOWN;
1278end;
1279
1280class function TProtocolExceptionInvalidData.GetType: TProtocolException.TExceptionType;
1281begin
1282 result := TExceptionType.INVALID_DATA;
1283end;
1284
1285class function TProtocolExceptionNegativeSize.GetType: TProtocolException.TExceptionType;
1286begin
1287 result := TExceptionType.NEGATIVE_SIZE;
1288end;
1289
1290class function TProtocolExceptionSizeLimit.GetType: TProtocolException.TExceptionType;
1291begin
1292 result := TExceptionType.SIZE_LIMIT;
1293end;
1294
1295class function TProtocolExceptionBadVersion.GetType: TProtocolException.TExceptionType;
1296begin
1297 result := TExceptionType.BAD_VERSION;
1298end;
1299
1300class function TProtocolExceptionNotImplemented.GetType: TProtocolException.TExceptionType;
1301begin
1302 result := TExceptionType.NOT_IMPLEMENTED;
1303end;
1304
1305class function TProtocolExceptionDepthLimit.GetType: TProtocolException.TExceptionType;
1306begin
1307 result := TExceptionType.DEPTH_LIMIT;
1308end;
1309
Jens Geyerd5436f52014-10-03 19:50:38 +02001310{ TBinaryProtocolImpl.TFactory }
1311
Jens Geyerfad7fd32019-11-09 23:24:52 +01001312constructor TBinaryProtocolImpl.TFactory.Create( const aStrictRead, aStrictWrite: Boolean);
Jens Geyerd5436f52014-10-03 19:50:38 +02001313begin
1314 inherited Create;
1315 FStrictRead := AStrictRead;
1316 FStrictWrite := AStrictWrite;
1317end;
1318
Jens Geyerd5436f52014-10-03 19:50:38 +02001319function TBinaryProtocolImpl.TFactory.GetProtocol( const trans: ITransport): IProtocol;
1320begin
1321 Result := TBinaryProtocolImpl.Create( trans, FStrictRead, FStrictWrite);
1322end;
1323
1324
1325{ TProtocolDecorator }
1326
1327constructor TProtocolDecorator.Create( const aProtocol : IProtocol);
1328begin
1329 ASSERT( aProtocol <> nil);
1330 inherited Create( aProtocol.Transport);
1331 FWrappedProtocol := aProtocol;
1332end;
1333
1334
Jens Geyer17c3ad92017-09-05 20:31:27 +02001335procedure TProtocolDecorator.WriteMessageBegin( const msg: TThriftMessage);
Jens Geyerd5436f52014-10-03 19:50:38 +02001336begin
1337 FWrappedProtocol.WriteMessageBegin( msg);
1338end;
1339
1340
1341procedure TProtocolDecorator.WriteMessageEnd;
1342begin
1343 FWrappedProtocol.WriteMessageEnd;
1344end;
1345
1346
Jens Geyer17c3ad92017-09-05 20:31:27 +02001347procedure TProtocolDecorator.WriteStructBegin( const struc: TThriftStruct);
Jens Geyerd5436f52014-10-03 19:50:38 +02001348begin
1349 FWrappedProtocol.WriteStructBegin( struc);
1350end;
1351
1352
1353procedure TProtocolDecorator.WriteStructEnd;
1354begin
1355 FWrappedProtocol.WriteStructEnd;
1356end;
1357
1358
Jens Geyer17c3ad92017-09-05 20:31:27 +02001359procedure TProtocolDecorator.WriteFieldBegin( const field: TThriftField);
Jens Geyerd5436f52014-10-03 19:50:38 +02001360begin
1361 FWrappedProtocol.WriteFieldBegin( field);
1362end;
1363
1364
1365procedure TProtocolDecorator.WriteFieldEnd;
1366begin
1367 FWrappedProtocol.WriteFieldEnd;
1368end;
1369
1370
1371procedure TProtocolDecorator.WriteFieldStop;
1372begin
1373 FWrappedProtocol.WriteFieldStop;
1374end;
1375
1376
Jens Geyer17c3ad92017-09-05 20:31:27 +02001377procedure TProtocolDecorator.WriteMapBegin( const map: TThriftMap);
Jens Geyerd5436f52014-10-03 19:50:38 +02001378begin
1379 FWrappedProtocol.WriteMapBegin( map);
1380end;
1381
1382
1383procedure TProtocolDecorator.WriteMapEnd;
1384begin
1385 FWrappedProtocol.WriteMapEnd;
1386end;
1387
1388
Jens Geyer17c3ad92017-09-05 20:31:27 +02001389procedure TProtocolDecorator.WriteListBegin( const list: TThriftList);
Jens Geyerd5436f52014-10-03 19:50:38 +02001390begin
1391 FWrappedProtocol.WriteListBegin( list);
1392end;
1393
1394
1395procedure TProtocolDecorator.WriteListEnd();
1396begin
1397 FWrappedProtocol.WriteListEnd();
1398end;
1399
1400
Jens Geyer17c3ad92017-09-05 20:31:27 +02001401procedure TProtocolDecorator.WriteSetBegin( const set_: TThriftSet );
Jens Geyerd5436f52014-10-03 19:50:38 +02001402begin
1403 FWrappedProtocol.WriteSetBegin( set_);
1404end;
1405
1406
1407procedure TProtocolDecorator.WriteSetEnd();
1408begin
1409 FWrappedProtocol.WriteSetEnd();
1410end;
1411
1412
1413procedure TProtocolDecorator.WriteBool( b: Boolean);
1414begin
1415 FWrappedProtocol.WriteBool( b);
1416end;
1417
1418
1419procedure TProtocolDecorator.WriteByte( b: ShortInt);
1420begin
1421 FWrappedProtocol.WriteByte( b);
1422end;
1423
1424
1425procedure TProtocolDecorator.WriteI16( i16: SmallInt);
1426begin
1427 FWrappedProtocol.WriteI16( i16);
1428end;
1429
1430
1431procedure TProtocolDecorator.WriteI32( i32: Integer);
1432begin
1433 FWrappedProtocol.WriteI32( i32);
1434end;
1435
1436
1437procedure TProtocolDecorator.WriteI64( const i64: Int64);
1438begin
1439 FWrappedProtocol.WriteI64( i64);
1440end;
1441
1442
1443procedure TProtocolDecorator.WriteDouble( const d: Double);
1444begin
1445 FWrappedProtocol.WriteDouble( d);
1446end;
1447
1448
1449procedure TProtocolDecorator.WriteString( const s: string );
1450begin
1451 FWrappedProtocol.WriteString( s);
1452end;
1453
1454
1455procedure TProtocolDecorator.WriteAnsiString( const s: AnsiString);
1456begin
1457 FWrappedProtocol.WriteAnsiString( s);
1458end;
1459
1460
1461procedure TProtocolDecorator.WriteBinary( const b: TBytes);
1462begin
1463 FWrappedProtocol.WriteBinary( b);
1464end;
1465
1466
Jens Geyer62445c12022-06-29 00:00:00 +02001467procedure TProtocolDecorator.WriteUuid( const uuid: TGuid);
1468begin
1469 FWrappedProtocol.WriteUuid( uuid);
1470end;
1471
1472
Jens Geyer17c3ad92017-09-05 20:31:27 +02001473function TProtocolDecorator.ReadMessageBegin: TThriftMessage;
Jens Geyerd5436f52014-10-03 19:50:38 +02001474begin
1475 result := FWrappedProtocol.ReadMessageBegin;
1476end;
1477
1478
1479procedure TProtocolDecorator.ReadMessageEnd();
1480begin
1481 FWrappedProtocol.ReadMessageEnd();
1482end;
1483
1484
Jens Geyer17c3ad92017-09-05 20:31:27 +02001485function TProtocolDecorator.ReadStructBegin: TThriftStruct;
Jens Geyerd5436f52014-10-03 19:50:38 +02001486begin
1487 result := FWrappedProtocol.ReadStructBegin;
1488end;
1489
1490
1491procedure TProtocolDecorator.ReadStructEnd;
1492begin
1493 FWrappedProtocol.ReadStructEnd;
1494end;
1495
1496
Jens Geyer17c3ad92017-09-05 20:31:27 +02001497function TProtocolDecorator.ReadFieldBegin: TThriftField;
Jens Geyerd5436f52014-10-03 19:50:38 +02001498begin
1499 result := FWrappedProtocol.ReadFieldBegin;
1500end;
1501
1502
1503procedure TProtocolDecorator.ReadFieldEnd();
1504begin
1505 FWrappedProtocol.ReadFieldEnd();
1506end;
1507
1508
Jens Geyer17c3ad92017-09-05 20:31:27 +02001509function TProtocolDecorator.ReadMapBegin: TThriftMap;
Jens Geyerd5436f52014-10-03 19:50:38 +02001510begin
1511 result := FWrappedProtocol.ReadMapBegin;
1512end;
1513
1514
1515procedure TProtocolDecorator.ReadMapEnd();
1516begin
1517 FWrappedProtocol.ReadMapEnd();
1518end;
1519
1520
Jens Geyer17c3ad92017-09-05 20:31:27 +02001521function TProtocolDecorator.ReadListBegin: TThriftList;
Jens Geyerd5436f52014-10-03 19:50:38 +02001522begin
1523 result := FWrappedProtocol.ReadListBegin;
1524end;
1525
1526
1527procedure TProtocolDecorator.ReadListEnd();
1528begin
1529 FWrappedProtocol.ReadListEnd();
1530end;
1531
1532
Jens Geyer17c3ad92017-09-05 20:31:27 +02001533function TProtocolDecorator.ReadSetBegin: TThriftSet;
Jens Geyerd5436f52014-10-03 19:50:38 +02001534begin
1535 result := FWrappedProtocol.ReadSetBegin;
1536end;
1537
1538
1539procedure TProtocolDecorator.ReadSetEnd();
1540begin
1541 FWrappedProtocol.ReadSetEnd();
1542end;
1543
1544
1545function TProtocolDecorator.ReadBool: Boolean;
1546begin
1547 result := FWrappedProtocol.ReadBool;
1548end;
1549
1550
1551function TProtocolDecorator.ReadByte: ShortInt;
1552begin
1553 result := FWrappedProtocol.ReadByte;
1554end;
1555
1556
1557function TProtocolDecorator.ReadI16: SmallInt;
1558begin
1559 result := FWrappedProtocol.ReadI16;
1560end;
1561
1562
1563function TProtocolDecorator.ReadI32: Integer;
1564begin
1565 result := FWrappedProtocol.ReadI32;
1566end;
1567
1568
1569function TProtocolDecorator.ReadI64: Int64;
1570begin
1571 result := FWrappedProtocol.ReadI64;
1572end;
1573
1574
1575function TProtocolDecorator.ReadDouble:Double;
1576begin
1577 result := FWrappedProtocol.ReadDouble;
1578end;
1579
1580
1581function TProtocolDecorator.ReadBinary: TBytes;
1582begin
1583 result := FWrappedProtocol.ReadBinary;
1584end;
1585
1586
Jens Geyer62445c12022-06-29 00:00:00 +02001587function TProtocolDecorator.ReadUuid: TGuid;
1588begin
1589 result := FWrappedProtocol.ReadUuid;
1590end;
1591
1592
Jens Geyerd5436f52014-10-03 19:50:38 +02001593function TProtocolDecorator.ReadString: string;
1594begin
1595 result := FWrappedProtocol.ReadString;
1596end;
1597
1598
1599function TProtocolDecorator.ReadAnsiString: AnsiString;
1600begin
1601 result := FWrappedProtocol.ReadAnsiString;
1602end;
1603
1604
Jens Geyer41f47af2019-11-09 23:24:52 +01001605function TProtocolDecorator.GetMinSerializedSize( const aType : TType) : Integer;
1606begin
1607 result := FWrappedProtocol.GetMinSerializedSize(aType);
1608end;
1609
1610
Jens Geyer17c3ad92017-09-05 20:31:27 +02001611{ Init helper functions }
1612
1613procedure Init( var rec : TThriftMessage; const AName: string; const AMessageType: TMessageType; const ASeqID: Integer);
1614begin
1615 rec.Name := AName;
1616 rec.Type_ := AMessageType;
1617 rec.SeqID := ASeqID;
1618end;
1619
1620
1621procedure Init( var rec : TThriftStruct; const AName: string = '');
1622begin
1623 rec.Name := AName;
1624end;
1625
1626
1627procedure Init( var rec : TThriftField; const AName: string; const AType: TType; const AID: SmallInt);
1628begin
1629 rec.Name := AName;
1630 rec.Type_ := AType;
1631 rec.Id := AId;
1632end;
1633
1634
1635procedure Init( var rec : TThriftMap; const AKeyType, AValueType: TType; const ACount: Integer);
1636begin
1637 rec.ValueType := AValueType;
1638 rec.KeyType := AKeyType;
1639 rec.Count := ACount;
1640end;
1641
1642
1643procedure Init( var rec : TThriftSet; const AElementType: TType; const ACount: Integer);
1644begin
1645 rec.Count := ACount;
1646 rec.ElementType := AElementType;
1647end;
1648
1649
1650procedure Init( var rec : TThriftList; const AElementType: TType; const ACount: Integer);
1651begin
1652 rec.Count := ACount;
1653 rec.ElementType := AElementType;
1654end;
1655
1656
1657
Jens Geyerd5436f52014-10-03 19:50:38 +02001658end.
1659