2 # Copyright (c) 2006- Facebook
3 # Distributed under the Thrift Software License
5 # See accompanying file LICENSE or visit the Thrift site at:
6 # http://developers.facebook.com/thrift/
8 # package - thrift.protocol.binary
9 # author - T Jake Luciani <jakers@gmail.com>
10 # author - Mark Slee <mcslee@facebook.com>
24 # Binary implementation of the Thrift protocol.
26 package Thrift
::BinaryProtocol
;
27 use base
('Thrift::Protocol');
29 use constant VERSION_MASK
=> 0xffff0000;
30 use constant VERSION_1
=> 0x80010000;
34 my $classname = shift;
36 my $self = $classname->SUPER::new
($trans);
38 return bless($self,$classname);
44 my ($name, $type, $seqid) = @_;
47 $self->writeI32(VERSION_1
| $type) +
48 $self->writeString($name) +
49 $self->writeI32($seqid);
73 my ($fieldName, $fieldType, $fieldId) = @_;
76 $self->writeByte($fieldType) +
77 $self->writeI16($fieldId);
89 return $self->writeByte(TType
::STOP
);
95 my ($keyType, $valType, $size) = @_;
98 $self->writeByte($keyType) +
99 $self->writeByte($valType) +
100 $self->writeI32($size);
112 my ($elemType, $size) = @_;
115 $self->writeByte($elemType) +
116 $self->writeI32($size);
128 my ($elemType, $size) = @_;
131 $self->writeByte($elemType) +
132 $self->writeI32($size);
146 my $data = pack('c', $value ?
1 : 0);
147 $self->{trans
}->write($data, 1);
156 my $data = pack('c', $value);
157 $self->{trans
}->write($data, 1);
166 my $data = pack('n', $value);
167 $self->{trans
}->write($data, 2);
176 my $data = pack('N', $value);
177 $self->{trans
}->write($data, 4);
189 $vec = Bit
::Vector
->new_Dec(64, $value);
190 $data = pack 'NN', $vec->Chunk_Read(32, 32), $vec->Chunk_Read(32, 0);
192 $self->{trans
}->write($data, 8);
203 my $data = pack('d', $value);
204 $self->{trans
}->write(scalar reverse($data), 8);
212 my $len = length($value);
214 my $result = $self->writeI32($len);
216 $self->{trans
}->write($value,$len);
218 return $result + $len;
228 my ($name, $type, $seqid) = @_;
231 my $result = $self->readI32(\
$version);
232 if (($version & VERSION_MASK
) > 0) {
233 if (($version & VERSION_MASK
) != VERSION_1
) {
234 die new Thrift
::TException
('Missing version identifier')
236 $$type = $version & 0x000000ff;
239 $self->readString($name) +
240 $self->readI32($seqid);
241 } else { # old client support code
244 $self->readStringBody($name, $version) + # version here holds the size of the string
245 $self->readByte($type) +
246 $self->readI32($seqid);
275 my ($name, $fieldType, $fieldId) = @_;
277 my $result = $self->readByte($fieldType);
279 if ($$fieldType == TType
::STOP
) {
284 $result += $self->readI16($fieldId);
297 my ($keyType, $valType, $size) = @_;
300 $self->readByte($keyType) +
301 $self->readByte($valType) +
302 $self->readI32($size);
314 my ($elemType, $size) = @_;
317 $self->readByte($elemType) +
318 $self->readI32($size);
330 my ($elemType, $size) = @_;
333 $self->readByte($elemType) +
334 $self->readI32($size);
348 my $data = $self->{trans
}->readAll(1);
349 my @arr = unpack('c', $data);
350 $$value = $arr[0] == 1;
359 my $data = $self->{trans
}->readAll(1);
360 my @arr = unpack('c', $data);
370 my $data = $self->{trans
}->readAll(2);
372 my @arr = unpack('n', $data);
376 if ($$value > 0x7fff) {
377 $$value = 0 - (($$value - 1) ^ 0xffff);
388 my $data = $self->{trans
}->readAll(4);
389 my @arr = unpack('N', $data);
392 if ($$value > 0x7fffffff) {
393 $$value = 0 - (($$value - 1) ^ 0xffffffff);
403 my $data = $self->{trans
}->readAll(8);
405 my ($hi,$lo)=unpack('NN',$data);
407 my $vec = new Bit
::Vector
(64);
409 $vec->Chunk_Store(32,32,$hi);
410 $vec->Chunk_Store(32,0,$lo);
412 $$value = $vec->to_Dec();
422 my $data = scalar reverse($self->{trans
}->readAll(8));
423 my @arr = unpack('d', $data);
436 my $result = $self->readI32(\
$len);
439 $$value = $self->{trans
}->readAll($len);
444 return $result + $len;
454 $$value = $self->{trans
}->readAll($len);
463 # Binary Protocol Factory
465 package TBinaryProtocolFactory
;
466 use base
('TProtocolFactory');
470 my $classname = shift;
471 my $self = $classname->SUPER::new
();
473 return bless($self,$classname);
480 return new TBinaryProtocol
($trans);