diff --git a/debian/gems-compat/thrift-0.11.0.0/README.md b/debian/gems-compat/thrift-0.11.0.0/README.md
new file mode 100644
index 0000000000..b6e9a0792f
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/README.md
@@ -0,0 +1,43 @@
+Thrift Ruby Software Library
+ http://thrift.apache.org
+
+== LICENSE:
+
+Licensed to the Apache Software Foundation (ASF) under one
+or more contributor license agreements. See the NOTICE file
+distributed with this work for additional information
+regarding copyright ownership. The ASF licenses this file
+to you under the Apache License, Version 2.0 (the
+"License"); you may not use this file except in compliance
+with the License. You may obtain a copy of the License at
+
+ http://www.apache.org/licenses/LICENSE-2.0
+
+Unless required by applicable law or agreed to in writing,
+software distributed under the License is distributed on an
+"AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+KIND, either express or implied. See the License for the
+specific language governing permissions and limitations
+under the License.
+
+== DESCRIPTION:
+
+Thrift is a strongly-typed language-agnostic RPC system.
+This library is the ruby implementation for both clients and servers.
+
+== INSTALL:
+
+ $ gem install thrift
+
+== CAVEATS:
+
+This library provides the client and server implementations of thrift.
+It does not provide the compiler for the .thrift files. To compile
+.thrift files into language-specific implementations, please download the full
+thrift software package.
+
+== USAGE:
+
+This section should get written by someone with the time and inclination.
+In the meantime, look at existing code, such as the benchmark or the tutorial
+in the full thrift distribution.
diff --git a/debian/gems-compat/thrift-0.11.0.0/benchmark/Benchmark.thrift b/debian/gems-compat/thrift-0.11.0.0/benchmark/Benchmark.thrift
new file mode 100644
index 0000000000..eb5ae38e6e
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/benchmark/Benchmark.thrift
@@ -0,0 +1,24 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+namespace rb ThriftBenchmark
+
+service BenchmarkService {
+ i32 fibonacci(1:byte n)
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/benchmark/benchmark.rb b/debian/gems-compat/thrift-0.11.0.0/benchmark/benchmark.rb
new file mode 100644
index 0000000000..3dc67dd8ce
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/benchmark/benchmark.rb
@@ -0,0 +1,271 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'rubygems'
+$:.unshift File.dirname(__FILE__) + '/../lib'
+require 'thrift'
+require 'stringio'
+
+HOST = '127.0.0.1'
+PORT = 42587
+
+###############
+## Server
+###############
+
+class Server
+ attr_accessor :serverclass
+ attr_accessor :interpreter
+ attr_accessor :host
+ attr_accessor :port
+
+ def initialize(opts)
+ @serverclass = opts.fetch(:class, Thrift::NonblockingServer)
+ @interpreter = opts.fetch(:interpreter, "ruby")
+ @host = opts.fetch(:host, ::HOST)
+ @port = opts.fetch(:port, ::PORT)
+ end
+
+ def start
+ return if @serverclass == Object
+ args = (File.basename(@interpreter) == "jruby" ? "-J-server" : "")
+ @pipe = IO.popen("#{@interpreter} #{args} #{File.dirname(__FILE__)}/server.rb #{@host} #{@port} #{@serverclass.name}", "r+")
+ Marshal.load(@pipe) # wait until the server has started
+ sleep 0.4 # give the server time to actually start spawning sockets
+ end
+
+ def shutdown
+ return unless @pipe
+ Marshal.dump(:shutdown, @pipe)
+ begin
+ @pipe.read(10) # block until the server shuts down
+ rescue EOFError
+ end
+ @pipe.close
+ @pipe = nil
+ end
+end
+
+class BenchmarkManager
+ def initialize(opts, server)
+ @socket = opts.fetch(:socket) do
+ @host = opts.fetch(:host, 'localhost')
+ @port = opts.fetch(:port)
+ nil
+ end
+ @num_processes = opts.fetch(:num_processes, 40)
+ @clients_per_process = opts.fetch(:clients_per_process, 10)
+ @calls_per_client = opts.fetch(:calls_per_client, 50)
+ @interpreter = opts.fetch(:interpreter, "ruby")
+ @server = server
+ @log_exceptions = opts.fetch(:log_exceptions, false)
+ end
+
+ def run
+ @pool = []
+ @benchmark_start = Time.now
+ puts "Spawning benchmark processes..."
+ @num_processes.times do
+ spawn
+ sleep 0.02 # space out spawns
+ end
+ collect_output
+ @benchmark_end = Time.now # we know the procs are done here
+ translate_output
+ analyze_output
+ report_output
+ end
+
+ def spawn
+ pipe = IO.popen("#{@interpreter} #{File.dirname(__FILE__)}/client.rb #{"-log-exceptions" if @log_exceptions} #{@host} #{@port} #{@clients_per_process} #{@calls_per_client}")
+ @pool << pipe
+ end
+
+ def socket_class
+ if @socket
+ Thrift::UNIXSocket
+ else
+ Thrift::Socket
+ end
+ end
+
+ def collect_output
+ puts "Collecting output..."
+ # read from @pool until all sockets are closed
+ @buffers = Hash.new { |h,k| h[k] = '' }
+ until @pool.empty?
+ rd, = select(@pool)
+ next if rd.nil?
+ rd.each do |fd|
+ begin
+ @buffers[fd] << fd.readpartial(4096)
+ rescue EOFError
+ @pool.delete fd
+ end
+ end
+ end
+ end
+
+ def translate_output
+ puts "Translating output..."
+ @output = []
+ @buffers.each do |fd, buffer|
+ strio = StringIO.new(buffer)
+ logs = []
+ begin
+ loop do
+ logs << Marshal.load(strio)
+ end
+ rescue EOFError
+ @output << logs
+ end
+ end
+ end
+
+ def analyze_output
+ puts "Analyzing output..."
+ call_times = []
+ client_times = []
+ connection_failures = []
+ connection_errors = []
+ shortest_call = 0
+ shortest_client = 0
+ longest_call = 0
+ longest_client = 0
+ @output.each do |logs|
+ cur_call, cur_client = nil
+ logs.each do |tok, time|
+ case tok
+ when :start
+ cur_client = time
+ when :call_start
+ cur_call = time
+ when :call_end
+ delta = time - cur_call
+ call_times << delta
+ longest_call = delta unless longest_call > delta
+ shortest_call = delta if shortest_call == 0 or delta < shortest_call
+ cur_call = nil
+ when :end
+ delta = time - cur_client
+ client_times << delta
+ longest_client = delta unless longest_client > delta
+ shortest_client = delta if shortest_client == 0 or delta < shortest_client
+ cur_client = nil
+ when :connection_failure
+ connection_failures << time
+ when :connection_error
+ connection_errors << time
+ end
+ end
+ end
+ @report = {}
+ @report[:total_calls] = call_times.inject(0.0) { |a,t| a += t }
+ @report[:avg_calls] = @report[:total_calls] / call_times.size
+ @report[:total_clients] = client_times.inject(0.0) { |a,t| a += t }
+ @report[:avg_clients] = @report[:total_clients] / client_times.size
+ @report[:connection_failures] = connection_failures.size
+ @report[:connection_errors] = connection_errors.size
+ @report[:shortest_call] = shortest_call
+ @report[:shortest_client] = shortest_client
+ @report[:longest_call] = longest_call
+ @report[:longest_client] = longest_client
+ @report[:total_benchmark_time] = @benchmark_end - @benchmark_start
+ @report[:fastthread] = $".include?('fastthread.bundle')
+ end
+
+ def report_output
+ fmt = "%.4f seconds"
+ puts
+ tabulate "%d",
+ [["Server class", "%s"], @server.serverclass == Object ? "" : @server.serverclass],
+ [["Server interpreter", "%s"], @server.interpreter],
+ [["Client interpreter", "%s"], @interpreter],
+ [["Socket class", "%s"], socket_class],
+ ["Number of processes", @num_processes],
+ ["Clients per process", @clients_per_process],
+ ["Calls per client", @calls_per_client],
+ [["Using fastthread", "%s"], @report[:fastthread] ? "yes" : "no"]
+ puts
+ failures = (@report[:connection_failures] > 0)
+ tabulate fmt,
+ [["Connection failures", "%d", [:red, :bold]], @report[:connection_failures]],
+ [["Connection errors", "%d", [:red, :bold]], @report[:connection_errors]],
+ ["Average time per call", @report[:avg_calls]],
+ ["Average time per client (%d calls)" % @calls_per_client, @report[:avg_clients]],
+ ["Total time for all calls", @report[:total_calls]],
+ ["Real time for benchmarking", @report[:total_benchmark_time]],
+ ["Shortest call time", @report[:shortest_call]],
+ ["Longest call time", @report[:longest_call]],
+ ["Shortest client time (%d calls)" % @calls_per_client, @report[:shortest_client]],
+ ["Longest client time (%d calls)" % @calls_per_client, @report[:longest_client]]
+ end
+
+ ANSI = {
+ :reset => 0,
+ :bold => 1,
+ :black => 30,
+ :red => 31,
+ :green => 32,
+ :yellow => 33,
+ :blue => 34,
+ :magenta => 35,
+ :cyan => 36,
+ :white => 37
+ }
+
+ def tabulate(fmt, *labels_and_values)
+ labels = labels_and_values.map { |l| Array === l ? l.first : l }
+ label_width = labels.inject(0) { |w,l| l.size > w ? l.size : w }
+ labels_and_values.each do |(l,v)|
+ f = fmt
+ l, f, c = l if Array === l
+ fmtstr = "%-#{label_width+1}s #{f}"
+ if STDOUT.tty? and c and v.to_i > 0
+ fmtstr = "\e[#{[*c].map { |x| ANSI[x] } * ";"}m" + fmtstr + "\e[#{ANSI[:reset]}m"
+ end
+ puts fmtstr % [l+":", v]
+ end
+ end
+end
+
+def resolve_const(const)
+ const and const.split('::').inject(Object) { |k,c| k.const_get(c) }
+end
+
+puts "Starting server..."
+args = {}
+args[:interpreter] = ENV['THRIFT_SERVER_INTERPRETER'] || ENV['THRIFT_INTERPRETER'] || "ruby"
+args[:class] = resolve_const(ENV['THRIFT_SERVER']) || Thrift::NonblockingServer
+args[:host] = ENV['THRIFT_HOST'] || HOST
+args[:port] = (ENV['THRIFT_PORT'] || PORT).to_i
+server = Server.new(args)
+server.start
+
+args = {}
+args[:host] = ENV['THRIFT_HOST'] || HOST
+args[:port] = (ENV['THRIFT_PORT'] || PORT).to_i
+args[:num_processes] = (ENV['THRIFT_NUM_PROCESSES'] || 40).to_i
+args[:clients_per_process] = (ENV['THRIFT_NUM_CLIENTS'] || 5).to_i
+args[:calls_per_client] = (ENV['THRIFT_NUM_CALLS'] || 50).to_i
+args[:interpreter] = ENV['THRIFT_CLIENT_INTERPRETER'] || ENV['THRIFT_INTERPRETER'] || "ruby"
+args[:log_exceptions] = !!ENV['THRIFT_LOG_EXCEPTIONS']
+BenchmarkManager.new(args, server).run
+
+server.shutdown
diff --git a/debian/gems-compat/thrift-0.11.0.0/benchmark/client.rb b/debian/gems-compat/thrift-0.11.0.0/benchmark/client.rb
new file mode 100644
index 0000000000..703dc8f521
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/benchmark/client.rb
@@ -0,0 +1,74 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+$:.unshift File.dirname(__FILE__) + '/../lib'
+require 'thrift'
+$:.unshift File.dirname(__FILE__) + "/gen-rb"
+require 'benchmark_service'
+
+class Client
+ def initialize(host, port, clients_per_process, calls_per_client, log_exceptions)
+ @host = host
+ @port = port
+ @clients_per_process = clients_per_process
+ @calls_per_client = calls_per_client
+ @log_exceptions = log_exceptions
+ end
+
+ def run
+ @clients_per_process.times do
+ socket = Thrift::Socket.new(@host, @port)
+ transport = Thrift::FramedTransport.new(socket)
+ protocol = Thrift::BinaryProtocol.new(transport)
+ client = ThriftBenchmark::BenchmarkService::Client.new(protocol)
+ begin
+ start = Time.now
+ transport.open
+ Marshal.dump [:start, start], STDOUT
+ rescue => e
+ Marshal.dump [:connection_failure, Time.now], STDOUT
+ print_exception e if @log_exceptions
+ else
+ begin
+ @calls_per_client.times do
+ Marshal.dump [:call_start, Time.now], STDOUT
+ client.fibonacci(15)
+ Marshal.dump [:call_end, Time.now], STDOUT
+ end
+ transport.close
+ Marshal.dump [:end, Time.now], STDOUT
+ rescue Thrift::TransportException => e
+ Marshal.dump [:connection_error, Time.now], STDOUT
+ print_exception e if @log_exceptions
+ end
+ end
+ end
+ end
+
+ def print_exception(e)
+ STDERR.puts "ERROR: #{e.message}"
+ STDERR.puts "\t#{e.backtrace * "\n\t"}"
+ end
+end
+
+log_exceptions = true if ARGV[0] == '-log-exceptions' and ARGV.shift
+
+host, port, clients_per_process, calls_per_client = ARGV
+
+Client.new(host, port.to_i, clients_per_process.to_i, calls_per_client.to_i, log_exceptions).run
diff --git a/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_constants.rb b/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_constants.rb
new file mode 100644
index 0000000000..c469a878fa
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_constants.rb
@@ -0,0 +1,11 @@
+#
+# Autogenerated by Thrift Compiler (0.11.0)
+#
+# DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+#
+
+require 'thrift'
+require 'benchmark_types'
+
+module ThriftBenchmark
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_service.rb b/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_service.rb
new file mode 100644
index 0000000000..5d60ed1874
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_service.rb
@@ -0,0 +1,80 @@
+#
+# Autogenerated by Thrift Compiler (0.11.0)
+#
+# DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+#
+
+require 'thrift'
+require 'benchmark_types'
+
+module ThriftBenchmark
+ module BenchmarkService
+ class Client
+ include ::Thrift::Client
+
+ def fibonacci(n)
+ send_fibonacci(n)
+ return recv_fibonacci()
+ end
+
+ def send_fibonacci(n)
+ send_message('fibonacci', Fibonacci_args, :n => n)
+ end
+
+ def recv_fibonacci()
+ result = receive_message(Fibonacci_result)
+ return result.success unless result.success.nil?
+ raise ::Thrift::ApplicationException.new(::Thrift::ApplicationException::MISSING_RESULT, 'fibonacci failed: unknown result')
+ end
+
+ end
+
+ class Processor
+ include ::Thrift::Processor
+
+ def process_fibonacci(seqid, iprot, oprot)
+ args = read_args(iprot, Fibonacci_args)
+ result = Fibonacci_result.new()
+ result.success = @handler.fibonacci(args.n)
+ write_result(result, oprot, 'fibonacci', seqid)
+ end
+
+ end
+
+ # HELPER FUNCTIONS AND STRUCTURES
+
+ class Fibonacci_args
+ include ::Thrift::Struct, ::Thrift::Struct_Union
+ N = 1
+
+ FIELDS = {
+ N => {:type => ::Thrift::Types::BYTE, :name => 'n'}
+ }
+
+ def struct_fields; FIELDS; end
+
+ def validate
+ end
+
+ ::Thrift::Struct.generate_accessors self
+ end
+
+ class Fibonacci_result
+ include ::Thrift::Struct, ::Thrift::Struct_Union
+ SUCCESS = 0
+
+ FIELDS = {
+ SUCCESS => {:type => ::Thrift::Types::I32, :name => 'success'}
+ }
+
+ def struct_fields; FIELDS; end
+
+ def validate
+ end
+
+ ::Thrift::Struct.generate_accessors self
+ end
+
+ end
+
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_types.rb b/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_types.rb
new file mode 100644
index 0000000000..94d7a083d1
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/benchmark/gen-rb/benchmark_types.rb
@@ -0,0 +1,10 @@
+#
+# Autogenerated by Thrift Compiler (0.11.0)
+#
+# DO NOT EDIT UNLESS YOU ARE SURE THAT YOU KNOW WHAT YOU ARE DOING
+#
+
+require 'thrift'
+
+module ThriftBenchmark
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/benchmark/server.rb b/debian/gems-compat/thrift-0.11.0.0/benchmark/server.rb
new file mode 100644
index 0000000000..74e13f4147
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/benchmark/server.rb
@@ -0,0 +1,82 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+$:.unshift File.dirname(__FILE__) + '/../lib'
+require 'thrift'
+$:.unshift File.dirname(__FILE__) + "/gen-rb"
+require 'benchmark_service'
+
+module Server
+ include Thrift
+
+ class BenchmarkHandler
+ # 1-based index into the fibonacci sequence
+ def fibonacci(n)
+ seq = [1, 1]
+ 3.upto(n) do
+ seq << seq[-1] + seq[-2]
+ end
+ seq[n-1] # n is 1-based
+ end
+ end
+
+ def self.start_server(host, port, serverClass)
+ handler = BenchmarkHandler.new
+ processor = ThriftBenchmark::BenchmarkService::Processor.new(handler)
+ transport = ServerSocket.new(host, port)
+ transport_factory = FramedTransportFactory.new
+ args = [processor, transport, transport_factory, nil, 20]
+ if serverClass == NonblockingServer
+ logger = Logger.new(STDERR)
+ logger.level = Logger::WARN
+ args << logger
+ end
+ server = serverClass.new(*args)
+ @server_thread = Thread.new do
+ server.serve
+ end
+ @server = server
+ end
+
+ def self.shutdown
+ return if @server.nil?
+ if @server.respond_to? :shutdown
+ @server.shutdown
+ else
+ @server_thread.kill
+ end
+ end
+end
+
+def resolve_const(const)
+ const and const.split('::').inject(Object) { |k,c| k.const_get(c) }
+end
+
+host, port, serverklass = ARGV
+
+Server.start_server(host, port.to_i, resolve_const(serverklass))
+
+# let our host know that the interpreter has started
+# ideally we'd wait until the server was serving, but we don't have a hook for that
+Marshal.dump(:started, STDOUT)
+STDOUT.flush
+
+Marshal.load(STDIN) # wait until we're instructed to shut down
+
+Server.shutdown
diff --git a/debian/gems-compat/thrift-0.11.0.0/benchmark/thin_server.rb b/debian/gems-compat/thrift-0.11.0.0/benchmark/thin_server.rb
new file mode 100644
index 0000000000..4de2eef382
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/benchmark/thin_server.rb
@@ -0,0 +1,44 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+$:.unshift File.dirname(__FILE__) + '/../lib'
+require 'thrift'
+$:.unshift File.dirname(__FILE__) + "/gen-rb"
+require 'benchmark_service'
+HOST = 'localhost'
+PORT = 42587
+
+class BenchmarkHandler
+ # 1-based index into the fibonacci sequence
+ def fibonacci(n)
+ seq = [1, 1]
+ 3.upto(n) do
+ seq << seq[-1] + seq[-2]
+ end
+ seq[n-1] # n is 1-based
+ end
+end
+
+handler = BenchmarkHandler.new
+processor = ThriftBenchmark::BenchmarkService::Processor.new(handler)
+transport = Thrift::ServerSocket.new(HOST, PORT)
+transport_factory = Thrift::FramedTransportFactory.new
+logger = Logger.new(STDERR)
+logger.level = Logger::WARN
+Thrift::NonblockingServer.new(processor, transport, transport_factory, nil, 20, logger).serve
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/binary_protocol_accelerated.c b/debian/gems-compat/thrift-0.11.0.0/ext/binary_protocol_accelerated.c
new file mode 100644
index 0000000000..65cbe5ffec
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/binary_protocol_accelerated.c
@@ -0,0 +1,460 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+VALUE rb_thrift_binary_proto_native_qmark(VALUE self) {
+ return Qtrue;
+}
+
+
+
+static int VERSION_1;
+static int VERSION_MASK;
+static int TYPE_MASK;
+static int BAD_VERSION;
+static ID rbuf_ivar_id;
+
+static void write_byte_direct(VALUE trans, int8_t b) {
+ WRITE(trans, (char*)&b, 1);
+}
+
+static void write_i16_direct(VALUE trans, int16_t value) {
+ char data[2];
+
+ data[1] = value;
+ data[0] = (value >> 8);
+
+ WRITE(trans, data, 2);
+}
+
+static void write_i32_direct(VALUE trans, int32_t value) {
+ char data[4];
+
+ data[3] = value;
+ data[2] = (value >> 8);
+ data[1] = (value >> 16);
+ data[0] = (value >> 24);
+
+ WRITE(trans, data, 4);
+}
+
+
+static void write_i64_direct(VALUE trans, int64_t value) {
+ char data[8];
+
+ data[7] = value;
+ data[6] = (value >> 8);
+ data[5] = (value >> 16);
+ data[4] = (value >> 24);
+ data[3] = (value >> 32);
+ data[2] = (value >> 40);
+ data[1] = (value >> 48);
+ data[0] = (value >> 56);
+
+ WRITE(trans, data, 8);
+}
+
+static void write_string_direct(VALUE trans, VALUE str) {
+ if (TYPE(str) != T_STRING) {
+ rb_raise(rb_eStandardError, "Value should be a string");
+ }
+ str = convert_to_utf8_byte_buffer(str);
+ write_i32_direct(trans, RSTRING_LEN(str));
+ rb_funcall(trans, write_method_id, 1, str);
+}
+
+//--------------------------------
+// interface writing methods
+//--------------------------------
+
+VALUE rb_thrift_binary_proto_write_message_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_struct_begin(VALUE self, VALUE name) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_struct_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_field_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_map_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_list_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_set_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_message_begin(VALUE self, VALUE name, VALUE type, VALUE seqid) {
+ VALUE trans = GET_TRANSPORT(self);
+ VALUE strict_write = GET_STRICT_WRITE(self);
+
+ if (strict_write == Qtrue) {
+ write_i32_direct(trans, VERSION_1 | FIX2INT(type));
+ write_string_direct(trans, name);
+ write_i32_direct(trans, FIX2INT(seqid));
+ } else {
+ write_string_direct(trans, name);
+ write_byte_direct(trans, FIX2INT(type));
+ write_i32_direct(trans, FIX2INT(seqid));
+ }
+
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_field_begin(VALUE self, VALUE name, VALUE type, VALUE id) {
+ VALUE trans = GET_TRANSPORT(self);
+ write_byte_direct(trans, FIX2INT(type));
+ write_i16_direct(trans, FIX2INT(id));
+
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_field_stop(VALUE self) {
+ write_byte_direct(GET_TRANSPORT(self), TTYPE_STOP);
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_map_begin(VALUE self, VALUE ktype, VALUE vtype, VALUE size) {
+ VALUE trans = GET_TRANSPORT(self);
+ write_byte_direct(trans, FIX2INT(ktype));
+ write_byte_direct(trans, FIX2INT(vtype));
+ write_i32_direct(trans, FIX2INT(size));
+
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_list_begin(VALUE self, VALUE etype, VALUE size) {
+ VALUE trans = GET_TRANSPORT(self);
+ write_byte_direct(trans, FIX2INT(etype));
+ write_i32_direct(trans, FIX2INT(size));
+
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_set_begin(VALUE self, VALUE etype, VALUE size) {
+ rb_thrift_binary_proto_write_list_begin(self, etype, size);
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_bool(VALUE self, VALUE b) {
+ write_byte_direct(GET_TRANSPORT(self), RTEST(b) ? 1 : 0);
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_byte(VALUE self, VALUE byte) {
+ CHECK_NIL(byte);
+ write_byte_direct(GET_TRANSPORT(self), NUM2INT(byte));
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_i16(VALUE self, VALUE i16) {
+ CHECK_NIL(i16);
+ write_i16_direct(GET_TRANSPORT(self), FIX2INT(i16));
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_i32(VALUE self, VALUE i32) {
+ CHECK_NIL(i32);
+ write_i32_direct(GET_TRANSPORT(self), NUM2INT(i32));
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_i64(VALUE self, VALUE i64) {
+ CHECK_NIL(i64);
+ write_i64_direct(GET_TRANSPORT(self), NUM2LL(i64));
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_double(VALUE self, VALUE dub) {
+ CHECK_NIL(dub);
+ // Unfortunately, bitwise_cast doesn't work in C. Bad C!
+ union {
+ double f;
+ int64_t t;
+ } transfer;
+ transfer.f = RFLOAT_VALUE(rb_Float(dub));
+ write_i64_direct(GET_TRANSPORT(self), transfer.t);
+
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_string(VALUE self, VALUE str) {
+ CHECK_NIL(str);
+ VALUE trans = GET_TRANSPORT(self);
+ write_string_direct(trans, str);
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_write_binary(VALUE self, VALUE buf) {
+ CHECK_NIL(buf);
+ VALUE trans = GET_TRANSPORT(self);
+ buf = force_binary_encoding(buf);
+ write_i32_direct(trans, RSTRING_LEN(buf));
+ rb_funcall(trans, write_method_id, 1, buf);
+ return Qnil;
+}
+
+//---------------------------------------
+// interface reading methods
+//---------------------------------------
+
+VALUE rb_thrift_binary_proto_read_string(VALUE self);
+VALUE rb_thrift_binary_proto_read_binary(VALUE self);
+VALUE rb_thrift_binary_proto_read_byte(VALUE self);
+VALUE rb_thrift_binary_proto_read_i32(VALUE self);
+VALUE rb_thrift_binary_proto_read_i16(VALUE self);
+
+static char read_byte_direct(VALUE self) {
+ VALUE byte = rb_funcall(GET_TRANSPORT(self), read_byte_method_id, 0);
+ return (char)(FIX2INT(byte));
+}
+
+static int16_t read_i16_direct(VALUE self) {
+ VALUE rbuf = rb_ivar_get(self, rbuf_ivar_id);
+ rb_funcall(GET_TRANSPORT(self), read_into_buffer_method_id, 2, rbuf, INT2FIX(2));
+ return (int16_t)(((uint8_t)(RSTRING_PTR(rbuf)[1])) | ((uint16_t)((RSTRING_PTR(rbuf)[0]) << 8)));
+}
+
+static int32_t read_i32_direct(VALUE self) {
+ VALUE rbuf = rb_ivar_get(self, rbuf_ivar_id);
+ rb_funcall(GET_TRANSPORT(self), read_into_buffer_method_id, 2, rbuf, INT2FIX(4));
+ return ((uint8_t)(RSTRING_PTR(rbuf)[3])) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[2])) << 8) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[1])) << 16) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[0])) << 24);
+}
+
+static int64_t read_i64_direct(VALUE self) {
+ VALUE rbuf = rb_ivar_get(self, rbuf_ivar_id);
+ rb_funcall(GET_TRANSPORT(self), read_into_buffer_method_id, 2, rbuf, INT2FIX(8));
+ uint64_t hi = ((uint8_t)(RSTRING_PTR(rbuf)[3])) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[2])) << 8) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[1])) << 16) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[0])) << 24);
+ uint32_t lo = ((uint8_t)(RSTRING_PTR(rbuf)[7])) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[6])) << 8) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[5])) << 16) |
+ (((uint8_t)(RSTRING_PTR(rbuf)[4])) << 24);
+ return (hi << 32) | lo;
+}
+
+static VALUE get_protocol_exception(VALUE code, VALUE message) {
+ VALUE args[2];
+ args[0] = code;
+ args[1] = message;
+ return rb_class_new_instance(2, (VALUE*)&args, protocol_exception_class);
+}
+
+VALUE rb_thrift_binary_proto_read_message_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_read_struct_begin(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_read_struct_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_read_field_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_read_map_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_read_list_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_read_set_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_binary_proto_read_message_begin(VALUE self) {
+ VALUE strict_read = GET_STRICT_READ(self);
+ VALUE name, seqid;
+ int type;
+
+ int version = read_i32_direct(self);
+
+ if (version < 0) {
+ if ((version & VERSION_MASK) != VERSION_1) {
+ rb_exc_raise(get_protocol_exception(INT2FIX(BAD_VERSION), rb_str_new2("Missing version identifier")));
+ }
+ type = version & TYPE_MASK;
+ name = rb_thrift_binary_proto_read_string(self);
+ seqid = rb_thrift_binary_proto_read_i32(self);
+ } else {
+ if (strict_read == Qtrue) {
+ rb_exc_raise(get_protocol_exception(INT2FIX(BAD_VERSION), rb_str_new2("No version identifier, old protocol client?")));
+ }
+ name = READ(self, version);
+ type = read_byte_direct(self);
+ seqid = rb_thrift_binary_proto_read_i32(self);
+ }
+
+ return rb_ary_new3(3, name, INT2FIX(type), seqid);
+}
+
+VALUE rb_thrift_binary_proto_read_field_begin(VALUE self) {
+ int type = read_byte_direct(self);
+ if (type == TTYPE_STOP) {
+ return rb_ary_new3(3, Qnil, INT2FIX(type), INT2FIX(0));
+ } else {
+ VALUE id = rb_thrift_binary_proto_read_i16(self);
+ return rb_ary_new3(3, Qnil, INT2FIX(type), id);
+ }
+}
+
+VALUE rb_thrift_binary_proto_read_map_begin(VALUE self) {
+ VALUE ktype = rb_thrift_binary_proto_read_byte(self);
+ VALUE vtype = rb_thrift_binary_proto_read_byte(self);
+ VALUE size = rb_thrift_binary_proto_read_i32(self);
+ return rb_ary_new3(3, ktype, vtype, size);
+}
+
+VALUE rb_thrift_binary_proto_read_list_begin(VALUE self) {
+ VALUE etype = rb_thrift_binary_proto_read_byte(self);
+ VALUE size = rb_thrift_binary_proto_read_i32(self);
+ return rb_ary_new3(2, etype, size);
+}
+
+VALUE rb_thrift_binary_proto_read_set_begin(VALUE self) {
+ return rb_thrift_binary_proto_read_list_begin(self);
+}
+
+VALUE rb_thrift_binary_proto_read_bool(VALUE self) {
+ char byte = read_byte_direct(self);
+ return byte != 0 ? Qtrue : Qfalse;
+}
+
+VALUE rb_thrift_binary_proto_read_byte(VALUE self) {
+ return INT2FIX(read_byte_direct(self));
+}
+
+VALUE rb_thrift_binary_proto_read_i16(VALUE self) {
+ return INT2FIX(read_i16_direct(self));
+}
+
+VALUE rb_thrift_binary_proto_read_i32(VALUE self) {
+ return INT2NUM(read_i32_direct(self));
+}
+
+VALUE rb_thrift_binary_proto_read_i64(VALUE self) {
+ return LL2NUM(read_i64_direct(self));
+}
+
+VALUE rb_thrift_binary_proto_read_double(VALUE self) {
+ union {
+ double f;
+ int64_t t;
+ } transfer;
+ transfer.t = read_i64_direct(self);
+ return rb_float_new(transfer.f);
+}
+
+VALUE rb_thrift_binary_proto_read_string(VALUE self) {
+ VALUE buffer = rb_thrift_binary_proto_read_binary(self);
+ return convert_to_string(buffer);
+}
+
+VALUE rb_thrift_binary_proto_read_binary(VALUE self) {
+ int size = read_i32_direct(self);
+ return READ(self, size);
+}
+
+void Init_binary_protocol_accelerated() {
+ VALUE thrift_binary_protocol_class = rb_const_get(thrift_module, rb_intern("BinaryProtocol"));
+
+ VERSION_1 = rb_num2ll(rb_const_get(thrift_binary_protocol_class, rb_intern("VERSION_1")));
+ VERSION_MASK = rb_num2ll(rb_const_get(thrift_binary_protocol_class, rb_intern("VERSION_MASK")));
+ TYPE_MASK = rb_num2ll(rb_const_get(thrift_binary_protocol_class, rb_intern("TYPE_MASK")));
+
+ VALUE bpa_class = rb_define_class_under(thrift_module, "BinaryProtocolAccelerated", thrift_binary_protocol_class);
+
+ rb_define_method(bpa_class, "native?", rb_thrift_binary_proto_native_qmark, 0);
+
+ rb_define_method(bpa_class, "write_message_begin", rb_thrift_binary_proto_write_message_begin, 3);
+ rb_define_method(bpa_class, "write_field_begin", rb_thrift_binary_proto_write_field_begin, 3);
+ rb_define_method(bpa_class, "write_field_stop", rb_thrift_binary_proto_write_field_stop, 0);
+ rb_define_method(bpa_class, "write_map_begin", rb_thrift_binary_proto_write_map_begin, 3);
+ rb_define_method(bpa_class, "write_list_begin", rb_thrift_binary_proto_write_list_begin, 2);
+ rb_define_method(bpa_class, "write_set_begin", rb_thrift_binary_proto_write_set_begin, 2);
+ rb_define_method(bpa_class, "write_byte", rb_thrift_binary_proto_write_byte, 1);
+ rb_define_method(bpa_class, "write_bool", rb_thrift_binary_proto_write_bool, 1);
+ rb_define_method(bpa_class, "write_i16", rb_thrift_binary_proto_write_i16, 1);
+ rb_define_method(bpa_class, "write_i32", rb_thrift_binary_proto_write_i32, 1);
+ rb_define_method(bpa_class, "write_i64", rb_thrift_binary_proto_write_i64, 1);
+ rb_define_method(bpa_class, "write_double", rb_thrift_binary_proto_write_double, 1);
+ rb_define_method(bpa_class, "write_string", rb_thrift_binary_proto_write_string, 1);
+ rb_define_method(bpa_class, "write_binary", rb_thrift_binary_proto_write_binary, 1);
+ // unused methods
+ rb_define_method(bpa_class, "write_message_end", rb_thrift_binary_proto_write_message_end, 0);
+ rb_define_method(bpa_class, "write_struct_begin", rb_thrift_binary_proto_write_struct_begin, 1);
+ rb_define_method(bpa_class, "write_struct_end", rb_thrift_binary_proto_write_struct_end, 0);
+ rb_define_method(bpa_class, "write_field_end", rb_thrift_binary_proto_write_field_end, 0);
+ rb_define_method(bpa_class, "write_map_end", rb_thrift_binary_proto_write_map_end, 0);
+ rb_define_method(bpa_class, "write_list_end", rb_thrift_binary_proto_write_list_end, 0);
+ rb_define_method(bpa_class, "write_set_end", rb_thrift_binary_proto_write_set_end, 0);
+
+ rb_define_method(bpa_class, "read_message_begin", rb_thrift_binary_proto_read_message_begin, 0);
+ rb_define_method(bpa_class, "read_field_begin", rb_thrift_binary_proto_read_field_begin, 0);
+ rb_define_method(bpa_class, "read_map_begin", rb_thrift_binary_proto_read_map_begin, 0);
+ rb_define_method(bpa_class, "read_list_begin", rb_thrift_binary_proto_read_list_begin, 0);
+ rb_define_method(bpa_class, "read_set_begin", rb_thrift_binary_proto_read_set_begin, 0);
+ rb_define_method(bpa_class, "read_byte", rb_thrift_binary_proto_read_byte, 0);
+ rb_define_method(bpa_class, "read_bool", rb_thrift_binary_proto_read_bool, 0);
+ rb_define_method(bpa_class, "read_i16", rb_thrift_binary_proto_read_i16, 0);
+ rb_define_method(bpa_class, "read_i32", rb_thrift_binary_proto_read_i32, 0);
+ rb_define_method(bpa_class, "read_i64", rb_thrift_binary_proto_read_i64, 0);
+ rb_define_method(bpa_class, "read_double", rb_thrift_binary_proto_read_double, 0);
+ rb_define_method(bpa_class, "read_string", rb_thrift_binary_proto_read_string, 0);
+ rb_define_method(bpa_class, "read_binary", rb_thrift_binary_proto_read_binary, 0);
+ // unused methods
+ rb_define_method(bpa_class, "read_message_end", rb_thrift_binary_proto_read_message_end, 0);
+ rb_define_method(bpa_class, "read_struct_begin", rb_thrift_binary_proto_read_struct_begin, 0);
+ rb_define_method(bpa_class, "read_struct_end", rb_thrift_binary_proto_read_struct_end, 0);
+ rb_define_method(bpa_class, "read_field_end", rb_thrift_binary_proto_read_field_end, 0);
+ rb_define_method(bpa_class, "read_map_end", rb_thrift_binary_proto_read_map_end, 0);
+ rb_define_method(bpa_class, "read_list_end", rb_thrift_binary_proto_read_list_end, 0);
+ rb_define_method(bpa_class, "read_set_end", rb_thrift_binary_proto_read_set_end, 0);
+
+ rbuf_ivar_id = rb_intern("@rbuf");
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/binary_protocol_accelerated.h b/debian/gems-compat/thrift-0.11.0.0/ext/binary_protocol_accelerated.h
new file mode 100644
index 0000000000..37baf4142f
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/binary_protocol_accelerated.h
@@ -0,0 +1,20 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+void Init_binary_protocol_accelerated();
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/bytes.c b/debian/gems-compat/thrift-0.11.0.0/ext/bytes.c
new file mode 100644
index 0000000000..8a6fac4ac4
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/bytes.c
@@ -0,0 +1,36 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include
+#ifdef HAVE_RUBY_ENCODING_H
+#include
+#endif
+#include
+
+VALUE force_binary_encoding(VALUE buffer) {
+ return rb_funcall(thrift_bytes_module, force_binary_encoding_id, 1, buffer);
+}
+
+VALUE convert_to_utf8_byte_buffer(VALUE string) {
+ return rb_funcall(thrift_bytes_module, convert_to_utf8_byte_buffer_id, 1, string);
+}
+
+VALUE convert_to_string(VALUE utf8_buffer) {
+ return rb_funcall(thrift_bytes_module, convert_to_string_id, 1, utf8_buffer);
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/bytes.h b/debian/gems-compat/thrift-0.11.0.0/ext/bytes.h
new file mode 100644
index 0000000000..7108d83ffc
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/bytes.h
@@ -0,0 +1,31 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include
+
+/*
+ * A collection of utilities for working with bytes and byte buffers.
+ *
+ * These methods are the native analogies to some of the methods in
+ * Thrift::Bytes (thrift/bytes.rb).
+ */
+
+VALUE force_binary_encoding(VALUE buffer);
+VALUE convert_to_utf8_byte_buffer(VALUE string);
+VALUE convert_to_string(VALUE utf8_buffer);
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/compact_protocol.c b/debian/gems-compat/thrift-0.11.0.0/ext/compact_protocol.c
new file mode 100644
index 0000000000..c0f46b9584
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/compact_protocol.c
@@ -0,0 +1,637 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include
+#include
+#include
+#include
+#include
+#include
+#include
+
+#define LAST_ID(obj) FIX2INT(rb_ary_pop(rb_ivar_get(obj, last_field_id)))
+#define SET_LAST_ID(obj, val) rb_ary_push(rb_ivar_get(obj, last_field_id), val)
+
+VALUE rb_thrift_compact_proto_native_qmark(VALUE self) {
+ return Qtrue;
+}
+
+static ID last_field_id;
+static ID boolean_field_id;
+static ID bool_value_id;
+static ID rbuf_ivar_id;
+
+static int VERSION;
+static int VERSION_MASK;
+static int TYPE_MASK;
+static int TYPE_BITS;
+static int TYPE_SHIFT_AMOUNT;
+static int PROTOCOL_ID;
+
+static VALUE thrift_compact_protocol_class;
+
+static int CTYPE_BOOLEAN_TRUE = 0x01;
+static int CTYPE_BOOLEAN_FALSE = 0x02;
+static int CTYPE_BYTE = 0x03;
+static int CTYPE_I16 = 0x04;
+static int CTYPE_I32 = 0x05;
+static int CTYPE_I64 = 0x06;
+static int CTYPE_DOUBLE = 0x07;
+static int CTYPE_BINARY = 0x08;
+static int CTYPE_LIST = 0x09;
+static int CTYPE_SET = 0x0A;
+static int CTYPE_MAP = 0x0B;
+static int CTYPE_STRUCT = 0x0C;
+
+VALUE rb_thrift_compact_proto_write_i16(VALUE self, VALUE i16);
+
+// TODO: implement this
+static int get_compact_type(VALUE type_value) {
+ int type = FIX2INT(type_value);
+ if (type == TTYPE_BOOL) {
+ return CTYPE_BOOLEAN_TRUE;
+ } else if (type == TTYPE_BYTE) {
+ return CTYPE_BYTE;
+ } else if (type == TTYPE_I16) {
+ return CTYPE_I16;
+ } else if (type == TTYPE_I32) {
+ return CTYPE_I32;
+ } else if (type == TTYPE_I64) {
+ return CTYPE_I64;
+ } else if (type == TTYPE_DOUBLE) {
+ return CTYPE_DOUBLE;
+ } else if (type == TTYPE_STRING) {
+ return CTYPE_BINARY;
+ } else if (type == TTYPE_LIST) {
+ return CTYPE_LIST;
+ } else if (type == TTYPE_SET) {
+ return CTYPE_SET;
+ } else if (type == TTYPE_MAP) {
+ return CTYPE_MAP;
+ } else if (type == TTYPE_STRUCT) {
+ return CTYPE_STRUCT;
+ } else {
+ char str[50];
+ sprintf(str, "don't know what type: %d", type);
+ rb_raise(rb_eStandardError, "%s", str);
+ return 0;
+ }
+}
+
+static void write_byte_direct(VALUE transport, int8_t b) {
+ WRITE(transport, (char*)&b, 1);
+}
+
+static void write_field_begin_internal(VALUE self, VALUE type, VALUE id_value, VALUE type_override) {
+ int id = FIX2INT(id_value);
+ int last_id = LAST_ID(self);
+ VALUE transport = GET_TRANSPORT(self);
+
+ // if there's a type override, use that.
+ int8_t type_to_write = RTEST(type_override) ? FIX2INT(type_override) : get_compact_type(type);
+ // check if we can use delta encoding for the field id
+ int diff = id - last_id;
+ if (diff > 0 && diff <= 15) {
+ // write them together
+ write_byte_direct(transport, diff << 4 | (type_to_write & 0x0f));
+ } else {
+ // write them separate
+ write_byte_direct(transport, type_to_write & 0x0f);
+ rb_thrift_compact_proto_write_i16(self, id_value);
+ }
+
+ SET_LAST_ID(self, id_value);
+}
+
+static int32_t int_to_zig_zag(int32_t n) {
+ return (n << 1) ^ (n >> 31);
+}
+
+static uint64_t ll_to_zig_zag(int64_t n) {
+ return (n << 1) ^ (n >> 63);
+}
+
+static void write_varint32(VALUE transport, uint32_t n) {
+ while (true) {
+ if ((n & ~0x7F) == 0) {
+ write_byte_direct(transport, n & 0x7f);
+ break;
+ } else {
+ write_byte_direct(transport, (n & 0x7F) | 0x80);
+ n = n >> 7;
+ }
+ }
+}
+
+static void write_varint64(VALUE transport, uint64_t n) {
+ while (true) {
+ if ((n & ~0x7F) == 0) {
+ write_byte_direct(transport, n & 0x7f);
+ break;
+ } else {
+ write_byte_direct(transport, (n & 0x7F) | 0x80);
+ n = n >> 7;
+ }
+ }
+}
+
+static void write_collection_begin(VALUE transport, VALUE elem_type, VALUE size_value) {
+ int size = FIX2INT(size_value);
+ if (size <= 14) {
+ write_byte_direct(transport, size << 4 | get_compact_type(elem_type));
+ } else {
+ write_byte_direct(transport, 0xf0 | get_compact_type(elem_type));
+ write_varint32(transport, size);
+ }
+}
+
+
+//--------------------------------
+// interface writing methods
+//--------------------------------
+
+VALUE rb_thrift_compact_proto_write_i32(VALUE self, VALUE i32);
+VALUE rb_thrift_compact_proto_write_string(VALUE self, VALUE str);
+VALUE rb_thrift_compact_proto_write_binary(VALUE self, VALUE buf);
+
+VALUE rb_thrift_compact_proto_write_message_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_struct_begin(VALUE self, VALUE name) {
+ rb_ary_push(rb_ivar_get(self, last_field_id), INT2FIX(0));
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_struct_end(VALUE self) {
+ rb_ary_pop(rb_ivar_get(self, last_field_id));
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_field_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_map_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_list_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_set_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_message_begin(VALUE self, VALUE name, VALUE type, VALUE seqid) {
+ VALUE transport = GET_TRANSPORT(self);
+ write_byte_direct(transport, PROTOCOL_ID);
+ write_byte_direct(transport, (VERSION & VERSION_MASK) | ((FIX2INT(type) << TYPE_SHIFT_AMOUNT) & TYPE_MASK));
+ write_varint32(transport, FIX2INT(seqid));
+ rb_thrift_compact_proto_write_string(self, name);
+
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_field_begin(VALUE self, VALUE name, VALUE type, VALUE id) {
+ if (FIX2INT(type) == TTYPE_BOOL) {
+ // we want to possibly include the value, so we'll wait.
+ rb_ivar_set(self, boolean_field_id, rb_ary_new3(2, type, id));
+ } else {
+ write_field_begin_internal(self, type, id, Qnil);
+ }
+
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_field_stop(VALUE self) {
+ write_byte_direct(GET_TRANSPORT(self), TTYPE_STOP);
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_map_begin(VALUE self, VALUE ktype, VALUE vtype, VALUE size_value) {
+ int size = FIX2INT(size_value);
+ VALUE transport = GET_TRANSPORT(self);
+ if (size == 0) {
+ write_byte_direct(transport, 0);
+ } else {
+ write_varint32(transport, size);
+ write_byte_direct(transport, get_compact_type(ktype) << 4 | get_compact_type(vtype));
+ }
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_list_begin(VALUE self, VALUE etype, VALUE size) {
+ write_collection_begin(GET_TRANSPORT(self), etype, size);
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_set_begin(VALUE self, VALUE etype, VALUE size) {
+ write_collection_begin(GET_TRANSPORT(self), etype, size);
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_bool(VALUE self, VALUE b) {
+ int8_t type = b == Qtrue ? CTYPE_BOOLEAN_TRUE : CTYPE_BOOLEAN_FALSE;
+ VALUE boolean_field = rb_ivar_get(self, boolean_field_id);
+ if (NIL_P(boolean_field)) {
+ // we're not part of a field, so just write the value.
+ write_byte_direct(GET_TRANSPORT(self), type);
+ } else {
+ // we haven't written the field header yet
+ write_field_begin_internal(self, rb_ary_entry(boolean_field, 0), rb_ary_entry(boolean_field, 1), INT2FIX(type));
+ rb_ivar_set(self, boolean_field_id, Qnil);
+ }
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_byte(VALUE self, VALUE byte) {
+ CHECK_NIL(byte);
+ write_byte_direct(GET_TRANSPORT(self), FIX2INT(byte));
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_i16(VALUE self, VALUE i16) {
+ rb_thrift_compact_proto_write_i32(self, i16);
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_i32(VALUE self, VALUE i32) {
+ CHECK_NIL(i32);
+ write_varint32(GET_TRANSPORT(self), int_to_zig_zag(NUM2INT(i32)));
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_i64(VALUE self, VALUE i64) {
+ CHECK_NIL(i64);
+ write_varint64(GET_TRANSPORT(self), ll_to_zig_zag(NUM2LL(i64)));
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_double(VALUE self, VALUE dub) {
+ CHECK_NIL(dub);
+ // Unfortunately, bitwise_cast doesn't work in C. Bad C!
+ union {
+ double f;
+ int64_t l;
+ } transfer;
+ transfer.f = RFLOAT_VALUE(rb_Float(dub));
+ char buf[8];
+ buf[0] = transfer.l & 0xff;
+ buf[1] = (transfer.l >> 8) & 0xff;
+ buf[2] = (transfer.l >> 16) & 0xff;
+ buf[3] = (transfer.l >> 24) & 0xff;
+ buf[4] = (transfer.l >> 32) & 0xff;
+ buf[5] = (transfer.l >> 40) & 0xff;
+ buf[6] = (transfer.l >> 48) & 0xff;
+ buf[7] = (transfer.l >> 56) & 0xff;
+ WRITE(GET_TRANSPORT(self), buf, 8);
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_string(VALUE self, VALUE str) {
+ str = convert_to_utf8_byte_buffer(str);
+ rb_thrift_compact_proto_write_binary(self, str);
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_write_binary(VALUE self, VALUE buf) {
+ buf = force_binary_encoding(buf);
+ VALUE transport = GET_TRANSPORT(self);
+ write_varint32(transport, RSTRING_LEN(buf));
+ WRITE(transport, StringValuePtr(buf), RSTRING_LEN(buf));
+ return Qnil;
+}
+
+//---------------------------------------
+// interface reading methods
+//---------------------------------------
+
+#define is_bool_type(ctype) (((ctype) & 0x0F) == CTYPE_BOOLEAN_TRUE || ((ctype) & 0x0F) == CTYPE_BOOLEAN_FALSE)
+
+VALUE rb_thrift_compact_proto_read_string(VALUE self);
+VALUE rb_thrift_compact_proto_read_binary(VALUE self);
+VALUE rb_thrift_compact_proto_read_byte(VALUE self);
+VALUE rb_thrift_compact_proto_read_i32(VALUE self);
+VALUE rb_thrift_compact_proto_read_i16(VALUE self);
+
+static int8_t get_ttype(int8_t ctype) {
+ if (ctype == TTYPE_STOP) {
+ return TTYPE_STOP;
+ } else if (ctype == CTYPE_BOOLEAN_TRUE || ctype == CTYPE_BOOLEAN_FALSE) {
+ return TTYPE_BOOL;
+ } else if (ctype == CTYPE_BYTE) {
+ return TTYPE_BYTE;
+ } else if (ctype == CTYPE_I16) {
+ return TTYPE_I16;
+ } else if (ctype == CTYPE_I32) {
+ return TTYPE_I32;
+ } else if (ctype == CTYPE_I64) {
+ return TTYPE_I64;
+ } else if (ctype == CTYPE_DOUBLE) {
+ return TTYPE_DOUBLE;
+ } else if (ctype == CTYPE_BINARY) {
+ return TTYPE_STRING;
+ } else if (ctype == CTYPE_LIST) {
+ return TTYPE_LIST;
+ } else if (ctype == CTYPE_SET) {
+ return TTYPE_SET;
+ } else if (ctype == CTYPE_MAP) {
+ return TTYPE_MAP;
+ } else if (ctype == CTYPE_STRUCT) {
+ return TTYPE_STRUCT;
+ } else {
+ char str[50];
+ sprintf(str, "don't know what type: %d", ctype);
+ rb_raise(rb_eStandardError, "%s", str);
+ return 0;
+ }
+}
+
+static char read_byte_direct(VALUE self) {
+ VALUE byte = rb_funcall(GET_TRANSPORT(self), read_byte_method_id, 0);
+ return (char)(FIX2INT(byte));
+}
+
+static int64_t zig_zag_to_ll(int64_t n) {
+ return (((uint64_t)n) >> 1) ^ -(n & 1);
+}
+
+static int32_t zig_zag_to_int(int32_t n) {
+ return (((uint32_t)n) >> 1) ^ -(n & 1);
+}
+
+static int64_t read_varint64(VALUE self) {
+ int shift = 0;
+ int64_t result = 0;
+ while (true) {
+ int8_t b = read_byte_direct(self);
+ result = result | ((uint64_t)(b & 0x7f) << shift);
+ if ((b & 0x80) != 0x80) {
+ break;
+ }
+ shift += 7;
+ }
+ return result;
+}
+
+static int16_t read_i16(VALUE self) {
+ return zig_zag_to_int((int32_t)read_varint64(self));
+}
+
+static VALUE get_protocol_exception(VALUE code, VALUE message) {
+ VALUE args[2];
+ args[0] = code;
+ args[1] = message;
+ return rb_class_new_instance(2, (VALUE*)&args, protocol_exception_class);
+}
+
+VALUE rb_thrift_compact_proto_read_message_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_read_struct_begin(VALUE self) {
+ rb_ary_push(rb_ivar_get(self, last_field_id), INT2FIX(0));
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_read_struct_end(VALUE self) {
+ rb_ary_pop(rb_ivar_get(self, last_field_id));
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_read_field_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_read_map_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_read_list_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_read_set_end(VALUE self) {
+ return Qnil;
+}
+
+VALUE rb_thrift_compact_proto_read_message_begin(VALUE self) {
+ int8_t protocol_id = read_byte_direct(self);
+ if (protocol_id != PROTOCOL_ID) {
+ char buf[100];
+ int len = sprintf(buf, "Expected protocol id %d but got %d", PROTOCOL_ID, protocol_id);
+ buf[len] = 0;
+ rb_exc_raise(get_protocol_exception(INT2FIX(-1), rb_str_new2(buf)));
+ }
+
+ int8_t version_and_type = read_byte_direct(self);
+ int8_t version = version_and_type & VERSION_MASK;
+ if (version != VERSION) {
+ char buf[100];
+ int len = sprintf(buf, "Expected version id %d but got %d", version, VERSION);
+ buf[len] = 0;
+ rb_exc_raise(get_protocol_exception(INT2FIX(-1), rb_str_new2(buf)));
+ }
+
+ int8_t type = (version_and_type >> TYPE_SHIFT_AMOUNT) & TYPE_BITS;
+ int32_t seqid = read_varint64(self);
+ VALUE messageName = rb_thrift_compact_proto_read_string(self);
+ return rb_ary_new3(3, messageName, INT2FIX(type), INT2NUM(seqid));
+}
+
+VALUE rb_thrift_compact_proto_read_field_begin(VALUE self) {
+ int8_t type = read_byte_direct(self);
+ // if it's a stop, then we can return immediately, as the struct is over.
+ if ((type & 0x0f) == TTYPE_STOP) {
+ return rb_ary_new3(3, Qnil, INT2FIX(0), INT2FIX(0));
+ } else {
+ int field_id = 0;
+
+ // mask off the 4 MSB of the type header. it could contain a field id delta.
+ uint8_t modifier = ((type & 0xf0) >> 4);
+
+ if (modifier == 0) {
+ // not a delta. look ahead for the zigzag varint field id.
+ (void) LAST_ID(self);
+ field_id = read_i16(self);
+ } else {
+ // has a delta. add the delta to the last read field id.
+ field_id = LAST_ID(self) + modifier;
+ }
+
+ // if this happens to be a boolean field, the value is encoded in the type
+ if (is_bool_type(type)) {
+ // save the boolean value in a special instance variable.
+ rb_ivar_set(self, bool_value_id, (type & 0x0f) == CTYPE_BOOLEAN_TRUE ? Qtrue : Qfalse);
+ }
+
+ // push the new field onto the field stack so we can keep the deltas going.
+ SET_LAST_ID(self, INT2FIX(field_id));
+ return rb_ary_new3(3, Qnil, INT2FIX(get_ttype(type & 0x0f)), INT2FIX(field_id));
+ }
+}
+
+VALUE rb_thrift_compact_proto_read_map_begin(VALUE self) {
+ int32_t size = read_varint64(self);
+ uint8_t key_and_value_type = size == 0 ? 0 : read_byte_direct(self);
+ return rb_ary_new3(3, INT2FIX(get_ttype(key_and_value_type >> 4)), INT2FIX(get_ttype(key_and_value_type & 0xf)), INT2FIX(size));
+}
+
+VALUE rb_thrift_compact_proto_read_list_begin(VALUE self) {
+ uint8_t size_and_type = read_byte_direct(self);
+ int32_t size = (size_and_type >> 4) & 0x0f;
+ if (size == 15) {
+ size = read_varint64(self);
+ }
+ uint8_t type = get_ttype(size_and_type & 0x0f);
+ return rb_ary_new3(2, INT2FIX(type), INT2FIX(size));
+}
+
+VALUE rb_thrift_compact_proto_read_set_begin(VALUE self) {
+ return rb_thrift_compact_proto_read_list_begin(self);
+}
+
+VALUE rb_thrift_compact_proto_read_bool(VALUE self) {
+ VALUE bool_value = rb_ivar_get(self, bool_value_id);
+ if (NIL_P(bool_value)) {
+ return read_byte_direct(self) == CTYPE_BOOLEAN_TRUE ? Qtrue : Qfalse;
+ } else {
+ rb_ivar_set(self, bool_value_id, Qnil);
+ return bool_value;
+ }
+}
+
+VALUE rb_thrift_compact_proto_read_byte(VALUE self) {
+ return INT2FIX(read_byte_direct(self));
+}
+
+VALUE rb_thrift_compact_proto_read_i16(VALUE self) {
+ return INT2FIX(read_i16(self));
+}
+
+VALUE rb_thrift_compact_proto_read_i32(VALUE self) {
+ return INT2NUM(zig_zag_to_int(read_varint64(self)));
+}
+
+VALUE rb_thrift_compact_proto_read_i64(VALUE self) {
+ return LL2NUM(zig_zag_to_ll(read_varint64(self)));
+}
+
+VALUE rb_thrift_compact_proto_read_double(VALUE self) {
+ union {
+ double f;
+ int64_t l;
+ } transfer;
+ VALUE rbuf = rb_ivar_get(self, rbuf_ivar_id);
+ rb_funcall(GET_TRANSPORT(self), read_into_buffer_method_id, 2, rbuf, INT2FIX(8));
+ uint32_t lo = ((uint8_t)(RSTRING_PTR(rbuf)[0]))
+ | (((uint8_t)(RSTRING_PTR(rbuf)[1])) << 8)
+ | (((uint8_t)(RSTRING_PTR(rbuf)[2])) << 16)
+ | (((uint8_t)(RSTRING_PTR(rbuf)[3])) << 24);
+ uint64_t hi = (((uint8_t)(RSTRING_PTR(rbuf)[4])))
+ | (((uint8_t)(RSTRING_PTR(rbuf)[5])) << 8)
+ | (((uint8_t)(RSTRING_PTR(rbuf)[6])) << 16)
+ | (((uint8_t)(RSTRING_PTR(rbuf)[7])) << 24);
+ transfer.l = (hi << 32) | lo;
+
+ return rb_float_new(transfer.f);
+}
+
+VALUE rb_thrift_compact_proto_read_string(VALUE self) {
+ VALUE buffer = rb_thrift_compact_proto_read_binary(self);
+ return convert_to_string(buffer);
+}
+
+VALUE rb_thrift_compact_proto_read_binary(VALUE self) {
+ int64_t size = read_varint64(self);
+ return READ(self, size);
+}
+
+static void Init_constants() {
+ thrift_compact_protocol_class = rb_const_get(thrift_module, rb_intern("CompactProtocol"));
+
+ VERSION = rb_num2ll(rb_const_get(thrift_compact_protocol_class, rb_intern("VERSION")));
+ VERSION_MASK = rb_num2ll(rb_const_get(thrift_compact_protocol_class, rb_intern("VERSION_MASK")));
+ TYPE_MASK = rb_num2ll(rb_const_get(thrift_compact_protocol_class, rb_intern("TYPE_MASK")));
+ TYPE_BITS = rb_num2ll(rb_const_get(thrift_compact_protocol_class, rb_intern("TYPE_BITS")));
+ TYPE_SHIFT_AMOUNT = FIX2INT(rb_const_get(thrift_compact_protocol_class, rb_intern("TYPE_SHIFT_AMOUNT")));
+ PROTOCOL_ID = FIX2INT(rb_const_get(thrift_compact_protocol_class, rb_intern("PROTOCOL_ID")));
+
+ last_field_id = rb_intern("@last_field");
+ boolean_field_id = rb_intern("@boolean_field");
+ bool_value_id = rb_intern("@bool_value");
+ rbuf_ivar_id = rb_intern("@rbuf");
+}
+
+static void Init_rb_methods() {
+ rb_define_method(thrift_compact_protocol_class, "native?", rb_thrift_compact_proto_native_qmark, 0);
+
+ rb_define_method(thrift_compact_protocol_class, "write_message_begin", rb_thrift_compact_proto_write_message_begin, 3);
+ rb_define_method(thrift_compact_protocol_class, "write_field_begin", rb_thrift_compact_proto_write_field_begin, 3);
+ rb_define_method(thrift_compact_protocol_class, "write_field_stop", rb_thrift_compact_proto_write_field_stop, 0);
+ rb_define_method(thrift_compact_protocol_class, "write_map_begin", rb_thrift_compact_proto_write_map_begin, 3);
+ rb_define_method(thrift_compact_protocol_class, "write_list_begin", rb_thrift_compact_proto_write_list_begin, 2);
+ rb_define_method(thrift_compact_protocol_class, "write_set_begin", rb_thrift_compact_proto_write_set_begin, 2);
+ rb_define_method(thrift_compact_protocol_class, "write_byte", rb_thrift_compact_proto_write_byte, 1);
+ rb_define_method(thrift_compact_protocol_class, "write_bool", rb_thrift_compact_proto_write_bool, 1);
+ rb_define_method(thrift_compact_protocol_class, "write_i16", rb_thrift_compact_proto_write_i16, 1);
+ rb_define_method(thrift_compact_protocol_class, "write_i32", rb_thrift_compact_proto_write_i32, 1);
+ rb_define_method(thrift_compact_protocol_class, "write_i64", rb_thrift_compact_proto_write_i64, 1);
+ rb_define_method(thrift_compact_protocol_class, "write_double", rb_thrift_compact_proto_write_double, 1);
+ rb_define_method(thrift_compact_protocol_class, "write_string", rb_thrift_compact_proto_write_string, 1);
+ rb_define_method(thrift_compact_protocol_class, "write_binary", rb_thrift_compact_proto_write_binary, 1);
+
+ rb_define_method(thrift_compact_protocol_class, "write_message_end", rb_thrift_compact_proto_write_message_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "write_struct_begin", rb_thrift_compact_proto_write_struct_begin, 1);
+ rb_define_method(thrift_compact_protocol_class, "write_struct_end", rb_thrift_compact_proto_write_struct_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "write_field_end", rb_thrift_compact_proto_write_field_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "write_map_end", rb_thrift_compact_proto_write_map_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "write_list_end", rb_thrift_compact_proto_write_list_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "write_set_end", rb_thrift_compact_proto_write_set_end, 0);
+
+
+ rb_define_method(thrift_compact_protocol_class, "read_message_begin", rb_thrift_compact_proto_read_message_begin, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_field_begin", rb_thrift_compact_proto_read_field_begin, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_map_begin", rb_thrift_compact_proto_read_map_begin, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_list_begin", rb_thrift_compact_proto_read_list_begin, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_set_begin", rb_thrift_compact_proto_read_set_begin, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_byte", rb_thrift_compact_proto_read_byte, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_bool", rb_thrift_compact_proto_read_bool, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_i16", rb_thrift_compact_proto_read_i16, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_i32", rb_thrift_compact_proto_read_i32, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_i64", rb_thrift_compact_proto_read_i64, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_double", rb_thrift_compact_proto_read_double, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_string", rb_thrift_compact_proto_read_string, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_binary", rb_thrift_compact_proto_read_binary, 0);
+
+ rb_define_method(thrift_compact_protocol_class, "read_message_end", rb_thrift_compact_proto_read_message_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_struct_begin", rb_thrift_compact_proto_read_struct_begin, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_struct_end", rb_thrift_compact_proto_read_struct_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_field_end", rb_thrift_compact_proto_read_field_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_map_end", rb_thrift_compact_proto_read_map_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_list_end", rb_thrift_compact_proto_read_list_end, 0);
+ rb_define_method(thrift_compact_protocol_class, "read_set_end", rb_thrift_compact_proto_read_set_end, 0);
+}
+
+void Init_compact_protocol() {
+ Init_constants();
+ Init_rb_methods();
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/compact_protocol.h b/debian/gems-compat/thrift-0.11.0.0/ext/compact_protocol.h
new file mode 100644
index 0000000000..163915e94f
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/compact_protocol.h
@@ -0,0 +1,20 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+void Init_compact_protocol();
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/constants.h b/debian/gems-compat/thrift-0.11.0.0/ext/constants.h
new file mode 100644
index 0000000000..e7aec44787
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/constants.h
@@ -0,0 +1,99 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+extern int TTYPE_STOP;
+extern int TTYPE_BOOL;
+extern int TTYPE_BYTE;
+extern int TTYPE_I16;
+extern int TTYPE_I32;
+extern int TTYPE_I64;
+extern int TTYPE_DOUBLE;
+extern int TTYPE_STRING;
+extern int TTYPE_MAP;
+extern int TTYPE_SET;
+extern int TTYPE_LIST;
+extern int TTYPE_STRUCT;
+
+extern ID validate_method_id;
+extern ID write_struct_begin_method_id;
+extern ID write_struct_end_method_id;
+extern ID write_field_begin_method_id;
+extern ID write_field_end_method_id;
+extern ID write_boolean_method_id;
+extern ID write_byte_method_id;
+extern ID write_i16_method_id;
+extern ID write_i32_method_id;
+extern ID write_i64_method_id;
+extern ID write_double_method_id;
+extern ID write_string_method_id;
+extern ID write_binary_method_id;
+extern ID write_map_begin_method_id;
+extern ID write_map_end_method_id;
+extern ID write_list_begin_method_id;
+extern ID write_list_end_method_id;
+extern ID write_set_begin_method_id;
+extern ID write_set_end_method_id;
+extern ID read_bool_method_id;
+extern ID read_byte_method_id;
+extern ID read_i16_method_id;
+extern ID read_i32_method_id;
+extern ID read_i64_method_id;
+extern ID read_string_method_id;
+extern ID read_binary_method_id;
+extern ID read_double_method_id;
+extern ID read_map_begin_method_id;
+extern ID read_map_end_method_id;
+extern ID read_list_begin_method_id;
+extern ID read_list_end_method_id;
+extern ID read_set_begin_method_id;
+extern ID read_set_end_method_id;
+extern ID read_struct_begin_method_id;
+extern ID read_struct_end_method_id;
+extern ID read_field_begin_method_id;
+extern ID read_field_end_method_id;
+extern ID keys_method_id;
+extern ID entries_method_id;
+extern ID write_field_stop_method_id;
+extern ID skip_method_id;
+extern ID write_method_id;
+extern ID read_all_method_id;
+extern ID read_into_buffer_method_id;
+extern ID force_binary_encoding_id;
+extern ID convert_to_utf8_byte_buffer_id;
+extern ID convert_to_string_id;
+
+extern ID fields_const_id;
+extern ID transport_ivar_id;
+extern ID strict_read_ivar_id;
+extern ID strict_write_ivar_id;
+
+extern VALUE type_sym;
+extern VALUE name_sym;
+extern VALUE key_sym;
+extern VALUE value_sym;
+extern VALUE element_sym;
+extern VALUE class_sym;
+extern VALUE binary_sym;
+
+extern VALUE rb_cSet;
+extern VALUE thrift_module;
+extern VALUE thrift_types_module;
+extern VALUE thrift_bytes_module;
+extern VALUE class_thrift_protocol;
+extern VALUE protocol_exception_class;
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/extconf.rb b/debian/gems-compat/thrift-0.11.0.0/ext/extconf.rb
new file mode 100644
index 0000000000..b35f60bf3a
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/extconf.rb
@@ -0,0 +1,34 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+if defined?(RUBY_ENGINE) && RUBY_ENGINE =~ /jruby/
+ File.open('Makefile', 'w'){|f| f.puts "all:\n\ninstall:\n" }
+else
+ require 'mkmf'
+ require 'rbconfig'
+
+ $ARCH_FLAGS = RbConfig::CONFIG['CFLAGS'].scan( /(-arch )(\S+)/ ).map{|x,y| x + y + ' ' }.join('')
+
+
+ $CFLAGS = "-fsigned-char -g -O2 -Wall -Werror " + $ARCH_FLAGS
+
+ have_func("strlcpy", "string.h")
+
+ create_makefile 'thrift_native'
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/macros.h b/debian/gems-compat/thrift-0.11.0.0/ext/macros.h
new file mode 100644
index 0000000000..265f6930d7
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/macros.h
@@ -0,0 +1,41 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#define GET_TRANSPORT(obj) rb_ivar_get(obj, transport_ivar_id)
+#define GET_STRICT_READ(obj) rb_ivar_get(obj, strict_read_ivar_id)
+#define GET_STRICT_WRITE(obj) rb_ivar_get(obj, strict_write_ivar_id)
+#define WRITE(obj, data, length) rb_funcall(obj, write_method_id, 1, rb_str_new(data, length))
+#define CHECK_NIL(obj) if (NIL_P(obj)) { rb_raise(rb_eStandardError, "nil argument not allowed!");}
+#define READ(obj, length) rb_funcall(GET_TRANSPORT(obj), read_all_method_id, 1, INT2FIX(length))
+
+#ifndef RFLOAT_VALUE
+# define RFLOAT_VALUE(v) RFLOAT(rb_Float(v))->value
+#endif
+
+#ifndef RSTRING_LEN
+# define RSTRING_LEN(v) RSTRING(rb_String(v))->len
+#endif
+
+#ifndef RSTRING_PTR
+# define RSTRING_PTR(v) RSTRING(rb_String(v))->ptr
+#endif
+
+#ifndef RARRAY_LEN
+# define RARRAY_LEN(v) RARRAY(rb_Array(v))->len
+#endif
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/memory_buffer.c b/debian/gems-compat/thrift-0.11.0.0/ext/memory_buffer.c
new file mode 100644
index 0000000000..8b52c4a3e0
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/memory_buffer.c
@@ -0,0 +1,134 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include
+#include
+#include
+#include
+
+ID buf_ivar_id;
+ID index_ivar_id;
+
+ID slice_method_id;
+
+int GARBAGE_BUFFER_SIZE;
+
+#define GET_BUF(self) rb_ivar_get(self, buf_ivar_id)
+
+VALUE rb_thrift_memory_buffer_write(VALUE self, VALUE str);
+VALUE rb_thrift_memory_buffer_read(VALUE self, VALUE length_value);
+VALUE rb_thrift_memory_buffer_read_byte(VALUE self);
+VALUE rb_thrift_memory_buffer_read_into_buffer(VALUE self, VALUE buffer_value, VALUE size_value);
+
+VALUE rb_thrift_memory_buffer_write(VALUE self, VALUE str) {
+ VALUE buf = GET_BUF(self);
+ str = force_binary_encoding(str);
+ rb_str_buf_cat(buf, StringValuePtr(str), RSTRING_LEN(str));
+ return Qnil;
+}
+
+VALUE rb_thrift_memory_buffer_read(VALUE self, VALUE length_value) {
+ int length = FIX2INT(length_value);
+
+ VALUE index_value = rb_ivar_get(self, index_ivar_id);
+ int index = FIX2INT(index_value);
+
+ VALUE buf = GET_BUF(self);
+ VALUE data = rb_funcall(buf, slice_method_id, 2, index_value, length_value);
+
+ index += length;
+ if (index > RSTRING_LEN(buf)) {
+ index = RSTRING_LEN(buf);
+ }
+ if (index >= GARBAGE_BUFFER_SIZE) {
+ rb_ivar_set(self, buf_ivar_id, rb_funcall(buf, slice_method_id, 2, INT2FIX(index), INT2FIX(RSTRING_LEN(buf) - 1)));
+ index = 0;
+ }
+ rb_ivar_set(self, index_ivar_id, INT2FIX(index));
+
+ if (RSTRING_LEN(data) < length) {
+ rb_raise(rb_eEOFError, "Not enough bytes remain in memory buffer");
+ }
+
+ return data;
+}
+
+VALUE rb_thrift_memory_buffer_read_byte(VALUE self) {
+ VALUE index_value = rb_ivar_get(self, index_ivar_id);
+ int index = FIX2INT(index_value);
+
+ VALUE buf = GET_BUF(self);
+ if (index >= RSTRING_LEN(buf)) {
+ rb_raise(rb_eEOFError, "Not enough bytes remain in memory buffer");
+ }
+ char byte = RSTRING_PTR(buf)[index++];
+
+ if (index >= GARBAGE_BUFFER_SIZE) {
+ rb_ivar_set(self, buf_ivar_id, rb_funcall(buf, slice_method_id, 2, INT2FIX(index), INT2FIX(RSTRING_LEN(buf) - 1)));
+ index = 0;
+ }
+ rb_ivar_set(self, index_ivar_id, INT2FIX(index));
+
+ int result = (int) byte;
+ return INT2FIX(result);
+}
+
+VALUE rb_thrift_memory_buffer_read_into_buffer(VALUE self, VALUE buffer_value, VALUE size_value) {
+ int i = 0;
+ int size = FIX2INT(size_value);
+ int index;
+ VALUE buf = GET_BUF(self);
+
+ index = FIX2INT(rb_ivar_get(self, index_ivar_id));
+ while (i < size) {
+ if (index >= RSTRING_LEN(buf)) {
+ rb_raise(rb_eEOFError, "Not enough bytes remain in memory buffer");
+ }
+ char byte = RSTRING_PTR(buf)[index++];
+
+ if (i >= RSTRING_LEN(buffer_value)) {
+ rb_raise(rb_eIndexError, "index %d out of string", i);
+ }
+ ((char*)RSTRING_PTR(buffer_value))[i] = byte;
+ i++;
+ }
+
+ if (index >= GARBAGE_BUFFER_SIZE) {
+ rb_ivar_set(self, buf_ivar_id, rb_funcall(buf, slice_method_id, 2, INT2FIX(index), INT2FIX(RSTRING_LEN(buf) - 1)));
+ index = 0;
+ }
+ rb_ivar_set(self, index_ivar_id, INT2FIX(index));
+
+ return INT2FIX(i);
+}
+
+void Init_memory_buffer() {
+ VALUE thrift_memory_buffer_class = rb_const_get(thrift_module, rb_intern("MemoryBufferTransport"));
+ rb_define_method(thrift_memory_buffer_class, "write", rb_thrift_memory_buffer_write, 1);
+ rb_define_method(thrift_memory_buffer_class, "read", rb_thrift_memory_buffer_read, 1);
+ rb_define_method(thrift_memory_buffer_class, "read_byte", rb_thrift_memory_buffer_read_byte, 0);
+ rb_define_method(thrift_memory_buffer_class, "read_into_buffer", rb_thrift_memory_buffer_read_into_buffer, 2);
+
+ buf_ivar_id = rb_intern("@buf");
+ index_ivar_id = rb_intern("@index");
+
+ slice_method_id = rb_intern("slice");
+
+ GARBAGE_BUFFER_SIZE = FIX2INT(rb_const_get(thrift_memory_buffer_class, rb_intern("GARBAGE_BUFFER_SIZE")));
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/memory_buffer.h b/debian/gems-compat/thrift-0.11.0.0/ext/memory_buffer.h
new file mode 100644
index 0000000000..b277fa6f6f
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/memory_buffer.h
@@ -0,0 +1,20 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+void Init_memory_buffer();
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/protocol.c b/debian/gems-compat/thrift-0.11.0.0/ext/protocol.c
new file mode 100644
index 0000000000..e69de29bb2
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/protocol.h b/debian/gems-compat/thrift-0.11.0.0/ext/protocol.h
new file mode 100644
index 0000000000..e69de29bb2
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/strlcpy.c b/debian/gems-compat/thrift-0.11.0.0/ext/strlcpy.c
new file mode 100644
index 0000000000..6700ff2d4f
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/strlcpy.c
@@ -0,0 +1,41 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include "strlcpy.h"
+
+#ifndef HAVE_STRLCPY
+#define HAVE_STRLCPY
+size_t
+strlcpy (char *dst, const char *src, size_t dst_sz)
+{
+ size_t n;
+
+ for (n = 0; n < dst_sz; n++) {
+ if ((*dst++ = *src++) == '\0')
+ break;
+ }
+
+ if (n < dst_sz)
+ return n;
+ if (n > 0)
+ *(dst - 1) = '\0';
+ return n + strlen (src);
+}
+#endif
+
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/strlcpy.h b/debian/gems-compat/thrift-0.11.0.0/ext/strlcpy.h
new file mode 100644
index 0000000000..f6fe0fe6b1
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/strlcpy.h
@@ -0,0 +1,34 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include
+#include
+
+#ifndef __has_builtin
+#define __has_builtin(x) 0
+#endif
+
+#ifndef HAVE_STRLCPY
+size_t strlcpy (char *dst, const char *src, size_t dst_sz);
+#else
+#if !__has_builtin(strlcpy)
+extern size_t strlcpy(char *, const char *, size_t);
+#endif
+#endif
+
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/struct.c b/debian/gems-compat/thrift-0.11.0.0/ext/struct.c
new file mode 100644
index 0000000000..e3aa855ed3
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/struct.c
@@ -0,0 +1,711 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include "struct.h"
+#include "constants.h"
+#include "macros.h"
+#include "strlcpy.h"
+
+VALUE thrift_union_class;
+
+ID setfield_id;
+ID setvalue_id;
+
+ID to_s_method_id;
+ID name_to_id_method_id;
+static ID sorted_field_ids_method_id;
+
+#define IS_CONTAINER(ttype) ((ttype) == TTYPE_MAP || (ttype) == TTYPE_LIST || (ttype) == TTYPE_SET)
+#define STRUCT_FIELDS(obj) rb_const_get(CLASS_OF(obj), fields_const_id)
+
+//-------------------------------------------
+// Writing section
+//-------------------------------------------
+
+// default fn pointers for protocol stuff here
+
+VALUE default_write_bool(VALUE protocol, VALUE value) {
+ rb_funcall(protocol, write_boolean_method_id, 1, value);
+ return Qnil;
+}
+
+VALUE default_write_byte(VALUE protocol, VALUE value) {
+ rb_funcall(protocol, write_byte_method_id, 1, value);
+ return Qnil;
+}
+
+VALUE default_write_i16(VALUE protocol, VALUE value) {
+ rb_funcall(protocol, write_i16_method_id, 1, value);
+ return Qnil;
+}
+
+VALUE default_write_i32(VALUE protocol, VALUE value) {
+ rb_funcall(protocol, write_i32_method_id, 1, value);
+ return Qnil;
+}
+
+VALUE default_write_i64(VALUE protocol, VALUE value) {
+ rb_funcall(protocol, write_i64_method_id, 1, value);
+ return Qnil;
+}
+
+VALUE default_write_double(VALUE protocol, VALUE value) {
+ rb_funcall(protocol, write_double_method_id, 1, value);
+ return Qnil;
+}
+
+VALUE default_write_string(VALUE protocol, VALUE value) {
+ rb_funcall(protocol, write_string_method_id, 1, value);
+ return Qnil;
+}
+
+VALUE default_write_binary(VALUE protocol, VALUE value) {
+ rb_funcall(protocol, write_binary_method_id, 1, value);
+ return Qnil;
+}
+
+VALUE default_write_list_begin(VALUE protocol, VALUE etype, VALUE length) {
+ rb_funcall(protocol, write_list_begin_method_id, 2, etype, length);
+ return Qnil;
+}
+
+VALUE default_write_list_end(VALUE protocol) {
+ rb_funcall(protocol, write_list_end_method_id, 0);
+ return Qnil;
+}
+
+VALUE default_write_set_begin(VALUE protocol, VALUE etype, VALUE length) {
+ rb_funcall(protocol, write_set_begin_method_id, 2, etype, length);
+ return Qnil;
+}
+
+VALUE default_write_set_end(VALUE protocol) {
+ rb_funcall(protocol, write_set_end_method_id, 0);
+ return Qnil;
+}
+
+VALUE default_write_map_begin(VALUE protocol, VALUE ktype, VALUE vtype, VALUE length) {
+ rb_funcall(protocol, write_map_begin_method_id, 3, ktype, vtype, length);
+ return Qnil;
+}
+
+VALUE default_write_map_end(VALUE protocol) {
+ rb_funcall(protocol, write_map_end_method_id, 0);
+ return Qnil;
+}
+
+VALUE default_write_struct_begin(VALUE protocol, VALUE struct_name) {
+ rb_funcall(protocol, write_struct_begin_method_id, 1, struct_name);
+ return Qnil;
+}
+
+VALUE default_write_struct_end(VALUE protocol) {
+ rb_funcall(protocol, write_struct_end_method_id, 0);
+ return Qnil;
+}
+
+VALUE default_write_field_begin(VALUE protocol, VALUE name, VALUE type, VALUE id) {
+ rb_funcall(protocol, write_field_begin_method_id, 3, name, type, id);
+ return Qnil;
+}
+
+VALUE default_write_field_end(VALUE protocol) {
+ rb_funcall(protocol, write_field_end_method_id, 0);
+ return Qnil;
+}
+
+VALUE default_write_field_stop(VALUE protocol) {
+ rb_funcall(protocol, write_field_stop_method_id, 0);
+ return Qnil;
+}
+
+VALUE default_read_field_begin(VALUE protocol) {
+ return rb_funcall(protocol, read_field_begin_method_id, 0);
+}
+
+VALUE default_read_field_end(VALUE protocol) {
+ return rb_funcall(protocol, read_field_end_method_id, 0);
+}
+
+VALUE default_read_map_begin(VALUE protocol) {
+ return rb_funcall(protocol, read_map_begin_method_id, 0);
+}
+
+VALUE default_read_map_end(VALUE protocol) {
+ return rb_funcall(protocol, read_map_end_method_id, 0);
+}
+
+VALUE default_read_list_begin(VALUE protocol) {
+ return rb_funcall(protocol, read_list_begin_method_id, 0);
+}
+
+VALUE default_read_list_end(VALUE protocol) {
+ return rb_funcall(protocol, read_list_end_method_id, 0);
+}
+
+VALUE default_read_set_begin(VALUE protocol) {
+ return rb_funcall(protocol, read_set_begin_method_id, 0);
+}
+
+VALUE default_read_set_end(VALUE protocol) {
+ return rb_funcall(protocol, read_set_end_method_id, 0);
+}
+
+VALUE default_read_byte(VALUE protocol) {
+ return rb_funcall(protocol, read_byte_method_id, 0);
+}
+
+VALUE default_read_bool(VALUE protocol) {
+ return rb_funcall(protocol, read_bool_method_id, 0);
+}
+
+VALUE default_read_i16(VALUE protocol) {
+ return rb_funcall(protocol, read_i16_method_id, 0);
+}
+
+VALUE default_read_i32(VALUE protocol) {
+ return rb_funcall(protocol, read_i32_method_id, 0);
+}
+
+VALUE default_read_i64(VALUE protocol) {
+ return rb_funcall(protocol, read_i64_method_id, 0);
+}
+
+VALUE default_read_double(VALUE protocol) {
+ return rb_funcall(protocol, read_double_method_id, 0);
+}
+
+VALUE default_read_string(VALUE protocol) {
+ return rb_funcall(protocol, read_string_method_id, 0);
+}
+
+VALUE default_read_binary(VALUE protocol) {
+ return rb_funcall(protocol, read_binary_method_id, 0);
+}
+
+VALUE default_read_struct_begin(VALUE protocol) {
+ return rb_funcall(protocol, read_struct_begin_method_id, 0);
+}
+
+VALUE default_read_struct_end(VALUE protocol) {
+ return rb_funcall(protocol, read_struct_end_method_id, 0);
+}
+
+// end default protocol methods
+
+static VALUE rb_thrift_union_write (VALUE self, VALUE protocol);
+static VALUE rb_thrift_struct_write(VALUE self, VALUE protocol);
+static void write_anything(int ttype, VALUE value, VALUE protocol, VALUE field_info);
+
+VALUE get_field_value(VALUE obj, VALUE field_name) {
+ char name_buf[RSTRING_LEN(field_name) + 2];
+
+ name_buf[0] = '@';
+ strlcpy(&name_buf[1], RSTRING_PTR(field_name), RSTRING_LEN(field_name) + 1);
+
+ VALUE value = rb_ivar_get(obj, rb_intern(name_buf));
+
+ return value;
+}
+
+static void write_container(int ttype, VALUE field_info, VALUE value, VALUE protocol) {
+ int sz, i;
+
+ if (ttype == TTYPE_MAP) {
+ VALUE keys;
+ VALUE key;
+ VALUE val;
+
+ Check_Type(value, T_HASH);
+
+ VALUE key_info = rb_hash_aref(field_info, key_sym);
+ VALUE keytype_value = rb_hash_aref(key_info, type_sym);
+ int keytype = FIX2INT(keytype_value);
+
+ VALUE value_info = rb_hash_aref(field_info, value_sym);
+ VALUE valuetype_value = rb_hash_aref(value_info, type_sym);
+ int valuetype = FIX2INT(valuetype_value);
+
+ keys = rb_funcall(value, keys_method_id, 0);
+
+ sz = RARRAY_LEN(keys);
+
+ default_write_map_begin(protocol, keytype_value, valuetype_value, INT2FIX(sz));
+
+ for (i = 0; i < sz; i++) {
+ key = rb_ary_entry(keys, i);
+ val = rb_hash_aref(value, key);
+
+ if (IS_CONTAINER(keytype)) {
+ write_container(keytype, key_info, key, protocol);
+ } else {
+ write_anything(keytype, key, protocol, key_info);
+ }
+
+ if (IS_CONTAINER(valuetype)) {
+ write_container(valuetype, value_info, val, protocol);
+ } else {
+ write_anything(valuetype, val, protocol, value_info);
+ }
+ }
+
+ default_write_map_end(protocol);
+ } else if (ttype == TTYPE_LIST) {
+ Check_Type(value, T_ARRAY);
+
+ sz = RARRAY_LEN(value);
+
+ VALUE element_type_info = rb_hash_aref(field_info, element_sym);
+ VALUE element_type_value = rb_hash_aref(element_type_info, type_sym);
+ int element_type = FIX2INT(element_type_value);
+
+ default_write_list_begin(protocol, element_type_value, INT2FIX(sz));
+ for (i = 0; i < sz; ++i) {
+ VALUE val = rb_ary_entry(value, i);
+ if (IS_CONTAINER(element_type)) {
+ write_container(element_type, element_type_info, val, protocol);
+ } else {
+ write_anything(element_type, val, protocol, element_type_info);
+ }
+ }
+ default_write_list_end(protocol);
+ } else if (ttype == TTYPE_SET) {
+ VALUE items;
+
+ if (TYPE(value) == T_ARRAY) {
+ items = value;
+ } else {
+ if (rb_cSet == CLASS_OF(value)) {
+ items = rb_funcall(value, entries_method_id, 0);
+ } else {
+ Check_Type(value, T_HASH);
+ items = rb_funcall(value, keys_method_id, 0);
+ }
+ }
+
+ sz = RARRAY_LEN(items);
+
+ VALUE element_type_info = rb_hash_aref(field_info, element_sym);
+ VALUE element_type_value = rb_hash_aref(element_type_info, type_sym);
+ int element_type = FIX2INT(element_type_value);
+
+ default_write_set_begin(protocol, element_type_value, INT2FIX(sz));
+
+ for (i = 0; i < sz; i++) {
+ VALUE val = rb_ary_entry(items, i);
+ if (IS_CONTAINER(element_type)) {
+ write_container(element_type, element_type_info, val, protocol);
+ } else {
+ write_anything(element_type, val, protocol, element_type_info);
+ }
+ }
+
+ default_write_set_end(protocol);
+ } else {
+ rb_raise(rb_eNotImpError, "can't write container of type: %d", ttype);
+ }
+}
+
+static void write_anything(int ttype, VALUE value, VALUE protocol, VALUE field_info) {
+ if (ttype == TTYPE_BOOL) {
+ default_write_bool(protocol, value);
+ } else if (ttype == TTYPE_BYTE) {
+ default_write_byte(protocol, value);
+ } else if (ttype == TTYPE_I16) {
+ default_write_i16(protocol, value);
+ } else if (ttype == TTYPE_I32) {
+ default_write_i32(protocol, value);
+ } else if (ttype == TTYPE_I64) {
+ default_write_i64(protocol, value);
+ } else if (ttype == TTYPE_DOUBLE) {
+ default_write_double(protocol, value);
+ } else if (ttype == TTYPE_STRING) {
+ VALUE is_binary = rb_hash_aref(field_info, binary_sym);
+ if (is_binary != Qtrue) {
+ default_write_string(protocol, value);
+ } else {
+ default_write_binary(protocol, value);
+ }
+ } else if (IS_CONTAINER(ttype)) {
+ write_container(ttype, field_info, value, protocol);
+ } else if (ttype == TTYPE_STRUCT) {
+ if (rb_obj_is_kind_of(value, thrift_union_class)) {
+ rb_thrift_union_write(value, protocol);
+ } else {
+ rb_thrift_struct_write(value, protocol);
+ }
+ } else {
+ rb_raise(rb_eNotImpError, "Unknown type for binary_encoding: %d", ttype);
+ }
+}
+
+static VALUE rb_thrift_struct_write(VALUE self, VALUE protocol) {
+ // call validate
+ rb_funcall(self, validate_method_id, 0);
+
+ // write struct begin
+ default_write_struct_begin(protocol, rb_class_name(CLASS_OF(self)));
+
+ // iterate through all the fields here
+ VALUE struct_fields = STRUCT_FIELDS(self);
+ VALUE sorted_field_ids = rb_funcall(self, sorted_field_ids_method_id, 0);
+
+ int i = 0;
+ for (i=0; i < RARRAY_LEN(sorted_field_ids); i++) {
+ VALUE field_id = rb_ary_entry(sorted_field_ids, i);
+
+ VALUE field_info = rb_hash_aref(struct_fields, field_id);
+
+ VALUE ttype_value = rb_hash_aref(field_info, type_sym);
+ int ttype = FIX2INT(ttype_value);
+ VALUE field_name = rb_hash_aref(field_info, name_sym);
+
+ VALUE field_value = get_field_value(self, field_name);
+
+ if (!NIL_P(field_value)) {
+ default_write_field_begin(protocol, field_name, ttype_value, field_id);
+
+ write_anything(ttype, field_value, protocol, field_info);
+
+ default_write_field_end(protocol);
+ }
+ }
+
+ default_write_field_stop(protocol);
+
+ // write struct end
+ default_write_struct_end(protocol);
+
+ return Qnil;
+}
+
+//-------------------------------------------
+// Reading section
+//-------------------------------------------
+
+static VALUE rb_thrift_union_read(VALUE self, VALUE protocol);
+static VALUE rb_thrift_struct_read(VALUE self, VALUE protocol);
+static void skip_map_contents(VALUE protocol, VALUE key_type_value, VALUE value_type_value, int size);
+static void skip_list_or_set_contents(VALUE protocol, VALUE element_type_value, int size);
+
+static void set_field_value(VALUE obj, VALUE field_name, VALUE value) {
+ char name_buf[RSTRING_LEN(field_name) + 2];
+
+ name_buf[0] = '@';
+ strlcpy(&name_buf[1], RSTRING_PTR(field_name), RSTRING_LEN(field_name)+1);
+
+ rb_ivar_set(obj, rb_intern(name_buf), value);
+}
+
+// Helper method to skip the contents of a map (assumes the map header has been read).
+static void skip_map_contents(VALUE protocol, VALUE key_type_value, VALUE value_type_value, int size) {
+ int i;
+ for (i = 0; i < size; i++) {
+ rb_funcall(protocol, skip_method_id, 1, key_type_value);
+ rb_funcall(protocol, skip_method_id, 1, value_type_value);
+ }
+}
+
+// Helper method to skip the contents of a list or set (assumes the list/set header has been read).
+static void skip_list_or_set_contents(VALUE protocol, VALUE element_type_value, int size) {
+ int i;
+ for (i = 0; i < size; i++) {
+ rb_funcall(protocol, skip_method_id, 1, element_type_value);
+ }
+}
+
+static VALUE read_anything(VALUE protocol, int ttype, VALUE field_info) {
+ VALUE result = Qnil;
+
+ if (ttype == TTYPE_BOOL) {
+ result = default_read_bool(protocol);
+ } else if (ttype == TTYPE_BYTE) {
+ result = default_read_byte(protocol);
+ } else if (ttype == TTYPE_I16) {
+ result = default_read_i16(protocol);
+ } else if (ttype == TTYPE_I32) {
+ result = default_read_i32(protocol);
+ } else if (ttype == TTYPE_I64) {
+ result = default_read_i64(protocol);
+ } else if (ttype == TTYPE_STRING) {
+ VALUE is_binary = rb_hash_aref(field_info, binary_sym);
+ if (is_binary != Qtrue) {
+ result = default_read_string(protocol);
+ } else {
+ result = default_read_binary(protocol);
+ }
+ } else if (ttype == TTYPE_DOUBLE) {
+ result = default_read_double(protocol);
+ } else if (ttype == TTYPE_STRUCT) {
+ VALUE klass = rb_hash_aref(field_info, class_sym);
+ result = rb_class_new_instance(0, NULL, klass);
+
+ if (rb_obj_is_kind_of(result, thrift_union_class)) {
+ rb_thrift_union_read(result, protocol);
+ } else {
+ rb_thrift_struct_read(result, protocol);
+ }
+ } else if (ttype == TTYPE_MAP) {
+ int i;
+
+ VALUE map_header = default_read_map_begin(protocol);
+ int key_ttype = FIX2INT(rb_ary_entry(map_header, 0));
+ int value_ttype = FIX2INT(rb_ary_entry(map_header, 1));
+ int num_entries = FIX2INT(rb_ary_entry(map_header, 2));
+
+ // Check the declared key and value types against the expected ones and skip the map contents
+ // if the types don't match.
+ VALUE key_info = rb_hash_aref(field_info, key_sym);
+ VALUE value_info = rb_hash_aref(field_info, value_sym);
+
+ if (!NIL_P(key_info) && !NIL_P(value_info)) {
+ int specified_key_type = FIX2INT(rb_hash_aref(key_info, type_sym));
+ int specified_value_type = FIX2INT(rb_hash_aref(value_info, type_sym));
+ if (num_entries == 0 || (specified_key_type == key_ttype && specified_value_type == value_ttype)) {
+ result = rb_hash_new();
+
+ for (i = 0; i < num_entries; ++i) {
+ VALUE key, val;
+
+ key = read_anything(protocol, key_ttype, key_info);
+ val = read_anything(protocol, value_ttype, value_info);
+
+ rb_hash_aset(result, key, val);
+ }
+ } else {
+ skip_map_contents(protocol, INT2FIX(key_ttype), INT2FIX(value_ttype), num_entries);
+ }
+ } else {
+ skip_map_contents(protocol, INT2FIX(key_ttype), INT2FIX(value_ttype), num_entries);
+ }
+
+ default_read_map_end(protocol);
+ } else if (ttype == TTYPE_LIST) {
+ int i;
+
+ VALUE list_header = default_read_list_begin(protocol);
+ int element_ttype = FIX2INT(rb_ary_entry(list_header, 0));
+ int num_elements = FIX2INT(rb_ary_entry(list_header, 1));
+
+ // Check the declared element type against the expected one and skip the list contents
+ // if the types don't match.
+ VALUE element_info = rb_hash_aref(field_info, element_sym);
+ if (!NIL_P(element_info)) {
+ int specified_element_type = FIX2INT(rb_hash_aref(element_info, type_sym));
+ if (specified_element_type == element_ttype) {
+ result = rb_ary_new2(num_elements);
+
+ for (i = 0; i < num_elements; ++i) {
+ rb_ary_push(result, read_anything(protocol, element_ttype, rb_hash_aref(field_info, element_sym)));
+ }
+ } else {
+ skip_list_or_set_contents(protocol, INT2FIX(element_ttype), num_elements);
+ }
+ } else {
+ skip_list_or_set_contents(protocol, INT2FIX(element_ttype), num_elements);
+ }
+
+ default_read_list_end(protocol);
+ } else if (ttype == TTYPE_SET) {
+ VALUE items;
+ int i;
+
+ VALUE set_header = default_read_set_begin(protocol);
+ int element_ttype = FIX2INT(rb_ary_entry(set_header, 0));
+ int num_elements = FIX2INT(rb_ary_entry(set_header, 1));
+
+ // Check the declared element type against the expected one and skip the set contents
+ // if the types don't match.
+ VALUE element_info = rb_hash_aref(field_info, element_sym);
+ if (!NIL_P(element_info)) {
+ int specified_element_type = FIX2INT(rb_hash_aref(element_info, type_sym));
+ if (specified_element_type == element_ttype) {
+ items = rb_ary_new2(num_elements);
+
+ for (i = 0; i < num_elements; ++i) {
+ rb_ary_push(items, read_anything(protocol, element_ttype, rb_hash_aref(field_info, element_sym)));
+ }
+
+ result = rb_class_new_instance(1, &items, rb_cSet);
+ } else {
+ skip_list_or_set_contents(protocol, INT2FIX(element_ttype), num_elements);
+ }
+ } else {
+ skip_list_or_set_contents(protocol, INT2FIX(element_ttype), num_elements);
+ }
+
+ default_read_set_end(protocol);
+ } else {
+ rb_raise(rb_eNotImpError, "read_anything not implemented for type %d!", ttype);
+ }
+
+ return result;
+}
+
+static VALUE rb_thrift_struct_read(VALUE self, VALUE protocol) {
+ // read struct begin
+ default_read_struct_begin(protocol);
+
+ VALUE struct_fields = STRUCT_FIELDS(self);
+
+ // read each field
+ while (true) {
+ VALUE field_header = default_read_field_begin(protocol);
+ VALUE field_type_value = rb_ary_entry(field_header, 1);
+ int field_type = FIX2INT(field_type_value);
+
+ if (field_type == TTYPE_STOP) {
+ break;
+ }
+
+ // make sure we got a type we expected
+ VALUE field_info = rb_hash_aref(struct_fields, rb_ary_entry(field_header, 2));
+
+ if (!NIL_P(field_info)) {
+ int specified_type = FIX2INT(rb_hash_aref(field_info, type_sym));
+ if (field_type == specified_type) {
+ // read the value
+ VALUE name = rb_hash_aref(field_info, name_sym);
+ set_field_value(self, name, read_anything(protocol, field_type, field_info));
+ } else {
+ rb_funcall(protocol, skip_method_id, 1, field_type_value);
+ }
+ } else {
+ rb_funcall(protocol, skip_method_id, 1, field_type_value);
+ }
+
+ // read field end
+ default_read_field_end(protocol);
+ }
+
+ // read struct end
+ default_read_struct_end(protocol);
+
+ // call validate
+ rb_funcall(self, validate_method_id, 0);
+
+ return Qnil;
+}
+
+
+// --------------------------------
+// Union section
+// --------------------------------
+
+static VALUE rb_thrift_union_read(VALUE self, VALUE protocol) {
+ // read struct begin
+ default_read_struct_begin(protocol);
+
+ VALUE struct_fields = STRUCT_FIELDS(self);
+
+ VALUE field_header = default_read_field_begin(protocol);
+ VALUE field_type_value = rb_ary_entry(field_header, 1);
+ int field_type = FIX2INT(field_type_value);
+
+ // make sure we got a type we expected
+ VALUE field_info = rb_hash_aref(struct_fields, rb_ary_entry(field_header, 2));
+
+ if (!NIL_P(field_info)) {
+ int specified_type = FIX2INT(rb_hash_aref(field_info, type_sym));
+ if (field_type == specified_type) {
+ // read the value
+ VALUE name = rb_hash_aref(field_info, name_sym);
+ rb_iv_set(self, "@setfield", rb_str_intern(name));
+ rb_iv_set(self, "@value", read_anything(protocol, field_type, field_info));
+ } else {
+ rb_funcall(protocol, skip_method_id, 1, field_type_value);
+ }
+ } else {
+ rb_funcall(protocol, skip_method_id, 1, field_type_value);
+ }
+
+ // read field end
+ default_read_field_end(protocol);
+
+ field_header = default_read_field_begin(protocol);
+ field_type_value = rb_ary_entry(field_header, 1);
+ field_type = FIX2INT(field_type_value);
+
+ if (field_type != TTYPE_STOP) {
+ rb_raise(rb_eRuntimeError, "too many fields in union!");
+ }
+
+ // read struct end
+ default_read_struct_end(protocol);
+
+ // call validate
+ rb_funcall(self, validate_method_id, 0);
+
+ return Qnil;
+}
+
+static VALUE rb_thrift_union_write(VALUE self, VALUE protocol) {
+ // call validate
+ rb_funcall(self, validate_method_id, 0);
+
+ // write struct begin
+ default_write_struct_begin(protocol, rb_class_name(CLASS_OF(self)));
+
+ VALUE struct_fields = STRUCT_FIELDS(self);
+
+ VALUE setfield = rb_ivar_get(self, setfield_id);
+ VALUE setvalue = rb_ivar_get(self, setvalue_id);
+ VALUE field_id = rb_funcall(self, name_to_id_method_id, 1, rb_funcall(setfield, to_s_method_id, 0));
+
+ VALUE field_info = rb_hash_aref(struct_fields, field_id);
+
+ if(NIL_P(field_info)) {
+ rb_raise(rb_eRuntimeError, "set_field is not valid for this union!");
+ }
+
+ VALUE ttype_value = rb_hash_aref(field_info, type_sym);
+ int ttype = FIX2INT(ttype_value);
+
+ default_write_field_begin(protocol, setfield, ttype_value, field_id);
+
+ write_anything(ttype, setvalue, protocol, field_info);
+
+ default_write_field_end(protocol);
+
+ default_write_field_stop(protocol);
+
+ // write struct end
+ default_write_struct_end(protocol);
+
+ return Qnil;
+}
+
+void Init_struct() {
+ VALUE struct_module = rb_const_get(thrift_module, rb_intern("Struct"));
+
+ rb_define_method(struct_module, "write", rb_thrift_struct_write, 1);
+ rb_define_method(struct_module, "read", rb_thrift_struct_read, 1);
+
+ thrift_union_class = rb_const_get(thrift_module, rb_intern("Union"));
+
+ rb_define_method(thrift_union_class, "write", rb_thrift_union_write, 1);
+ rb_define_method(thrift_union_class, "read", rb_thrift_union_read, 1);
+
+ setfield_id = rb_intern("@setfield");
+ setvalue_id = rb_intern("@value");
+
+ to_s_method_id = rb_intern("to_s");
+ name_to_id_method_id = rb_intern("name_to_id");
+ sorted_field_ids_method_id = rb_intern("sorted_field_ids");
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/struct.h b/debian/gems-compat/thrift-0.11.0.0/ext/struct.h
new file mode 100644
index 0000000000..4748be5cb6
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/struct.h
@@ -0,0 +1,25 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+
+#include
+#include
+
+void Init_struct();
+void Init_union();
diff --git a/debian/gems-compat/thrift-0.11.0.0/ext/thrift_native.c b/debian/gems-compat/thrift-0.11.0.0/ext/thrift_native.c
new file mode 100644
index 0000000000..3430b7c254
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/ext/thrift_native.c
@@ -0,0 +1,201 @@
+/**
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#include
+#include
+#include
+#include
+#include
+#include
+
+// cached classes/modules
+VALUE rb_cSet;
+VALUE thrift_module;
+VALUE thrift_bytes_module;
+VALUE thrift_types_module;
+
+// TType constants
+int TTYPE_STOP;
+int TTYPE_BOOL;
+int TTYPE_BYTE;
+int TTYPE_I16;
+int TTYPE_I32;
+int TTYPE_I64;
+int TTYPE_DOUBLE;
+int TTYPE_STRING;
+int TTYPE_MAP;
+int TTYPE_SET;
+int TTYPE_LIST;
+int TTYPE_STRUCT;
+
+// method ids
+ID validate_method_id;
+ID write_struct_begin_method_id;
+ID write_struct_end_method_id;
+ID write_field_begin_method_id;
+ID write_field_end_method_id;
+ID write_boolean_method_id;
+ID write_byte_method_id;
+ID write_i16_method_id;
+ID write_i32_method_id;
+ID write_i64_method_id;
+ID write_double_method_id;
+ID write_string_method_id;
+ID write_binary_method_id;
+ID write_map_begin_method_id;
+ID write_map_end_method_id;
+ID write_list_begin_method_id;
+ID write_list_end_method_id;
+ID write_set_begin_method_id;
+ID write_set_end_method_id;
+ID read_bool_method_id;
+ID read_byte_method_id;
+ID read_i16_method_id;
+ID read_i32_method_id;
+ID read_i64_method_id;
+ID read_string_method_id;
+ID read_binary_method_id;
+ID read_double_method_id;
+ID read_map_begin_method_id;
+ID read_map_end_method_id;
+ID read_list_begin_method_id;
+ID read_list_end_method_id;
+ID read_set_begin_method_id;
+ID read_set_end_method_id;
+ID read_struct_begin_method_id;
+ID read_struct_end_method_id;
+ID read_field_begin_method_id;
+ID read_field_end_method_id;
+ID keys_method_id;
+ID entries_method_id;
+ID write_field_stop_method_id;
+ID skip_method_id;
+ID write_method_id;
+ID read_all_method_id;
+ID read_into_buffer_method_id;
+ID force_binary_encoding_id;
+ID convert_to_utf8_byte_buffer_id;
+ID convert_to_string_id;
+
+// constant ids
+ID fields_const_id;
+ID transport_ivar_id;
+ID strict_read_ivar_id;
+ID strict_write_ivar_id;
+
+// cached symbols
+VALUE type_sym;
+VALUE name_sym;
+VALUE key_sym;
+VALUE value_sym;
+VALUE element_sym;
+VALUE class_sym;
+VALUE binary_sym;
+VALUE protocol_exception_class;
+
+void Init_thrift_native() {
+ // cached classes
+ thrift_module = rb_const_get(rb_cObject, rb_intern("Thrift"));
+ thrift_bytes_module = rb_const_get(thrift_module, rb_intern("Bytes"));
+ thrift_types_module = rb_const_get(thrift_module, rb_intern("Types"));
+ rb_cSet = rb_const_get(rb_cObject, rb_intern("Set"));
+ protocol_exception_class = rb_const_get(thrift_module, rb_intern("ProtocolException"));
+
+ // Init ttype constants
+ TTYPE_BOOL = FIX2INT(rb_const_get(thrift_types_module, rb_intern("BOOL")));
+ TTYPE_BYTE = FIX2INT(rb_const_get(thrift_types_module, rb_intern("BYTE")));
+ TTYPE_I16 = FIX2INT(rb_const_get(thrift_types_module, rb_intern("I16")));
+ TTYPE_I32 = FIX2INT(rb_const_get(thrift_types_module, rb_intern("I32")));
+ TTYPE_I64 = FIX2INT(rb_const_get(thrift_types_module, rb_intern("I64")));
+ TTYPE_DOUBLE = FIX2INT(rb_const_get(thrift_types_module, rb_intern("DOUBLE")));
+ TTYPE_STRING = FIX2INT(rb_const_get(thrift_types_module, rb_intern("STRING")));
+ TTYPE_MAP = FIX2INT(rb_const_get(thrift_types_module, rb_intern("MAP")));
+ TTYPE_SET = FIX2INT(rb_const_get(thrift_types_module, rb_intern("SET")));
+ TTYPE_LIST = FIX2INT(rb_const_get(thrift_types_module, rb_intern("LIST")));
+ TTYPE_STRUCT = FIX2INT(rb_const_get(thrift_types_module, rb_intern("STRUCT")));
+
+ // method ids
+ validate_method_id = rb_intern("validate");
+ write_struct_begin_method_id = rb_intern("write_struct_begin");
+ write_struct_end_method_id = rb_intern("write_struct_end");
+ write_field_begin_method_id = rb_intern("write_field_begin");
+ write_field_end_method_id = rb_intern("write_field_end");
+ write_boolean_method_id = rb_intern("write_bool");
+ write_byte_method_id = rb_intern("write_byte");
+ write_i16_method_id = rb_intern("write_i16");
+ write_i32_method_id = rb_intern("write_i32");
+ write_i64_method_id = rb_intern("write_i64");
+ write_double_method_id = rb_intern("write_double");
+ write_string_method_id = rb_intern("write_string");
+ write_binary_method_id = rb_intern("write_binary");
+ write_map_begin_method_id = rb_intern("write_map_begin");
+ write_map_end_method_id = rb_intern("write_map_end");
+ write_list_begin_method_id = rb_intern("write_list_begin");
+ write_list_end_method_id = rb_intern("write_list_end");
+ write_set_begin_method_id = rb_intern("write_set_begin");
+ write_set_end_method_id = rb_intern("write_set_end");
+ read_bool_method_id = rb_intern("read_bool");
+ read_byte_method_id = rb_intern("read_byte");
+ read_i16_method_id = rb_intern("read_i16");
+ read_i32_method_id = rb_intern("read_i32");
+ read_i64_method_id = rb_intern("read_i64");
+ read_string_method_id = rb_intern("read_string");
+ read_binary_method_id = rb_intern("read_binary");
+ read_double_method_id = rb_intern("read_double");
+ read_map_begin_method_id = rb_intern("read_map_begin");
+ read_map_end_method_id = rb_intern("read_map_end");
+ read_list_begin_method_id = rb_intern("read_list_begin");
+ read_list_end_method_id = rb_intern("read_list_end");
+ read_set_begin_method_id = rb_intern("read_set_begin");
+ read_set_end_method_id = rb_intern("read_set_end");
+ read_struct_begin_method_id = rb_intern("read_struct_begin");
+ read_struct_end_method_id = rb_intern("read_struct_end");
+ read_field_begin_method_id = rb_intern("read_field_begin");
+ read_field_end_method_id = rb_intern("read_field_end");
+ keys_method_id = rb_intern("keys");
+ entries_method_id = rb_intern("entries");
+ write_field_stop_method_id = rb_intern("write_field_stop");
+ skip_method_id = rb_intern("skip");
+ write_method_id = rb_intern("write");
+ read_all_method_id = rb_intern("read_all");
+ read_into_buffer_method_id = rb_intern("read_into_buffer");
+ force_binary_encoding_id = rb_intern("force_binary_encoding");
+ convert_to_utf8_byte_buffer_id = rb_intern("convert_to_utf8_byte_buffer");
+ convert_to_string_id = rb_intern("convert_to_string");
+
+ // constant ids
+ fields_const_id = rb_intern("FIELDS");
+ transport_ivar_id = rb_intern("@trans");
+ strict_read_ivar_id = rb_intern("@strict_read");
+ strict_write_ivar_id = rb_intern("@strict_write");
+
+ // cached symbols
+ type_sym = ID2SYM(rb_intern("type"));
+ name_sym = ID2SYM(rb_intern("name"));
+ key_sym = ID2SYM(rb_intern("key"));
+ value_sym = ID2SYM(rb_intern("value"));
+ element_sym = ID2SYM(rb_intern("element"));
+ class_sym = ID2SYM(rb_intern("class"));
+ binary_sym = ID2SYM(rb_intern("binary"));
+
+ Init_struct();
+ Init_binary_protocol_accelerated();
+ Init_compact_protocol();
+ Init_memory_buffer();
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift.rb
new file mode 100644
index 0000000000..0f581229c1
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift.rb
@@ -0,0 +1,70 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+# Contains some contributions under the Thrift Software License.
+# Please see doc/old-thrift-license.txt in the Thrift distribution for
+# details.
+
+$:.unshift File.dirname(__FILE__)
+
+require 'thrift/bytes'
+require 'thrift/core_ext'
+require 'thrift/exceptions'
+require 'thrift/types'
+require 'thrift/processor'
+require 'thrift/multiplexed_processor'
+require 'thrift/client'
+require 'thrift/struct'
+require 'thrift/union'
+require 'thrift/struct_union'
+
+# serializer
+require 'thrift/serializer/serializer'
+require 'thrift/serializer/deserializer'
+
+# protocol
+require 'thrift/protocol/base_protocol'
+require 'thrift/protocol/binary_protocol'
+require 'thrift/protocol/binary_protocol_accelerated'
+require 'thrift/protocol/compact_protocol'
+require 'thrift/protocol/json_protocol'
+require 'thrift/protocol/multiplexed_protocol'
+
+# transport
+require 'thrift/transport/base_transport'
+require 'thrift/transport/base_server_transport'
+require 'thrift/transport/socket'
+require 'thrift/transport/ssl_socket'
+require 'thrift/transport/server_socket'
+require 'thrift/transport/ssl_server_socket'
+require 'thrift/transport/unix_socket'
+require 'thrift/transport/unix_server_socket'
+require 'thrift/transport/buffered_transport'
+require 'thrift/transport/framed_transport'
+require 'thrift/transport/http_client_transport'
+require 'thrift/transport/io_stream_transport'
+require 'thrift/transport/memory_buffer_transport'
+
+# server
+require 'thrift/server/base_server'
+require 'thrift/server/nonblocking_server'
+require 'thrift/server/simple_server'
+require 'thrift/server/threaded_server'
+require 'thrift/server/thread_pool_server'
+
+require 'thrift/thrift_native'
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/bytes.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/bytes.rb
new file mode 100644
index 0000000000..efd4f6440c
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/bytes.rb
@@ -0,0 +1,131 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ # A collection of utilities for working with bytes and byte buffers.
+ module Bytes
+ if RUBY_VERSION >= '1.9'
+ # Creates and empty byte buffer (String with BINARY encoding)
+ #
+ # size - The Integer size of the buffer (default: nil) to create
+ #
+ # Returns a String with BINARY encoding, filled with null characters
+ # if size is greater than zero
+ def self.empty_byte_buffer(size = nil)
+ if (size && size > 0)
+ "\0".force_encoding(Encoding::BINARY) * size
+ else
+ ''.force_encoding(Encoding::BINARY)
+ end
+ end
+
+ # Forces the encoding of the buffer to BINARY. If the buffer
+ # passed is frozen, then it will be duplicated.
+ #
+ # buffer - The String to force the encoding of.
+ #
+ # Returns the String passed with an encoding of BINARY; returned
+ # String may be a duplicate.
+ def self.force_binary_encoding(buffer)
+ buffer = buffer.dup if buffer.frozen?
+ buffer.force_encoding(Encoding::BINARY)
+ end
+
+ # Gets the byte value of a given position in a String.
+ #
+ # string - The String to retrive the byte value from.
+ # index - The Integer location of the byte value to retrieve.
+ #
+ # Returns an Integer value between 0 and 255.
+ def self.get_string_byte(string, index)
+ string.getbyte(index)
+ end
+
+ # Sets the byte value given to a given index in a String.
+ #
+ # string - The String to set the byte value in.
+ # index - The Integer location to set the byte value at.
+ # byte - The Integer value (0 to 255) to set in the string.
+ #
+ # Returns an Integer value of the byte value to set.
+ def self.set_string_byte(string, index, byte)
+ string.setbyte(index, byte)
+ end
+
+ # Converts the given String to a UTF-8 byte buffer.
+ #
+ # string - The String to convert.
+ #
+ # Returns a new String with BINARY encoding, containing the UTF-8
+ # bytes of the original string.
+ def self.convert_to_utf8_byte_buffer(string)
+ if string.encoding != Encoding::UTF_8
+ # transcode to UTF-8
+ string = string.encode(Encoding::UTF_8)
+ else
+ # encoding is already UTF-8, but a duplicate is needed
+ string = string.dup
+ end
+ string.force_encoding(Encoding::BINARY)
+ end
+
+ # Converts the given UTF-8 byte buffer into a String
+ #
+ # utf8_buffer - A String, with BINARY encoding, containing UTF-8 bytes
+ #
+ # Returns a new String with UTF-8 encoding,
+ def self.convert_to_string(utf8_buffer)
+ # duplicate the buffer, force encoding to UTF-8
+ utf8_buffer.dup.force_encoding(Encoding::UTF_8)
+ end
+ else
+ def self.empty_byte_buffer(size = nil)
+ if (size && size > 0)
+ "\0" * size
+ else
+ ''
+ end
+ end
+
+ def self.force_binary_encoding(buffer)
+ buffer
+ end
+
+ def self.get_string_byte(string, index)
+ string[index]
+ end
+
+ def self.set_string_byte(string, index, byte)
+ string[index] = byte
+ end
+
+ def self.convert_to_utf8_byte_buffer(string)
+ # This assumes $KCODE is 'UTF8'/'U', which would mean the String is already a UTF-8 byte buffer
+ # TODO consider handling other $KCODE values and transcoding with iconv
+ string
+ end
+
+ def self.convert_to_string(utf8_buffer)
+ # See comment in 'convert_to_utf8_byte_buffer' for relevant assumptions.
+ utf8_buffer
+ end
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/client.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/client.rb
new file mode 100644
index 0000000000..64ef05956c
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/client.rb
@@ -0,0 +1,71 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ module Client
+ def initialize(iprot, oprot=nil)
+ @iprot = iprot
+ @oprot = oprot || iprot
+ @seqid = 0
+ end
+
+ def send_message(name, args_class, args = {})
+ @oprot.write_message_begin(name, MessageTypes::CALL, @seqid)
+ send_message_args(args_class, args)
+ end
+
+ def send_oneway_message(name, args_class, args = {})
+ @oprot.write_message_begin(name, MessageTypes::ONEWAY, @seqid)
+ send_message_args(args_class, args)
+ end
+
+ def send_message_args(args_class, args)
+ data = args_class.new
+ args.each do |k, v|
+ data.send("#{k.to_s}=", v)
+ end
+ begin
+ data.write(@oprot)
+ rescue StandardError => e
+ @oprot.trans.close
+ raise e
+ end
+ @oprot.write_message_end
+ @oprot.trans.flush
+ end
+
+ def receive_message(result_klass)
+ fname, mtype, rseqid = @iprot.read_message_begin
+ handle_exception(mtype)
+ result = result_klass.new
+ result.read(@iprot)
+ @iprot.read_message_end
+ result
+ end
+
+ def handle_exception(mtype)
+ if mtype == MessageTypes::EXCEPTION
+ x = ApplicationException.new
+ x.read(@iprot)
+ @iprot.read_message_end
+ raise x
+ end
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/core_ext.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/core_ext.rb
new file mode 100644
index 0000000000..f763cd5344
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/core_ext.rb
@@ -0,0 +1,23 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+Dir[File.dirname(__FILE__) + "/core_ext/*.rb"].each do |file|
+ name = File.basename(file, '.rb')
+ require "thrift/core_ext/#{name}"
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/core_ext/fixnum.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/core_ext/fixnum.rb
new file mode 100644
index 0000000000..b4fc90dd69
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/core_ext/fixnum.rb
@@ -0,0 +1,29 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+# Versions of ruby pre 1.8.7 do not have an .ord method available in the Fixnum
+# class.
+#
+if RUBY_VERSION < "1.8.7"
+ class Fixnum
+ def ord
+ self
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/exceptions.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/exceptions.rb
new file mode 100644
index 0000000000..68cb9e03ae
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/exceptions.rb
@@ -0,0 +1,87 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class Exception < StandardError
+ def initialize(message)
+ super
+ @message = message
+ end
+
+ attr_reader :message
+ end
+
+ class ApplicationException < Exception
+
+ UNKNOWN = 0
+ UNKNOWN_METHOD = 1
+ INVALID_MESSAGE_TYPE = 2
+ WRONG_METHOD_NAME = 3
+ BAD_SEQUENCE_ID = 4
+ MISSING_RESULT = 5
+ INTERNAL_ERROR = 6
+ PROTOCOL_ERROR = 7
+ INVALID_TRANSFORM = 8
+ INVALID_PROTOCOL = 9
+ UNSUPPORTED_CLIENT_TYPE = 10
+
+ attr_reader :type
+
+ def initialize(type=UNKNOWN, message=nil)
+ super(message)
+ @type = type
+ end
+
+ def read(iprot)
+ iprot.read_struct_begin
+ while true
+ fname, ftype, fid = iprot.read_field_begin
+ if ftype == Types::STOP
+ break
+ end
+ if fid == 1 and ftype == Types::STRING
+ @message = iprot.read_string
+ elsif fid == 2 and ftype == Types::I32
+ @type = iprot.read_i32
+ else
+ iprot.skip(ftype)
+ end
+ iprot.read_field_end
+ end
+ iprot.read_struct_end
+ end
+
+ def write(oprot)
+ oprot.write_struct_begin('Thrift::ApplicationException')
+ unless @message.nil?
+ oprot.write_field_begin('message', Types::STRING, 1)
+ oprot.write_string(@message)
+ oprot.write_field_end
+ end
+ unless @type.nil?
+ oprot.write_field_begin('type', Types::I32, 2)
+ oprot.write_i32(@type)
+ oprot.write_field_end
+ end
+ oprot.write_field_stop
+ oprot.write_struct_end
+ end
+
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/multiplexed_processor.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/multiplexed_processor.rb
new file mode 100644
index 0000000000..c734c04ba0
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/multiplexed_processor.rb
@@ -0,0 +1,76 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+
+require 'thrift/protocol/protocol_decorator'
+require 'thrift/protocol/base_protocol'
+
+module Thrift
+ class MultiplexedProcessor
+ def initialize
+ @actual_processors = {}
+ end
+
+ def register_processor(service_name, processor)
+ @actual_processors[service_name] = processor
+ end
+
+ def process(iprot, oprot)
+ name, type, seqid = iprot.read_message_begin
+ check_type(type)
+ check_separator(name)
+ service_name, method = name.split(':')
+ processor(service_name).process(StoredMessageProtocol.new(iprot, [method, type, seqid]), oprot)
+ end
+
+ protected
+
+ def processor(service_name)
+ if @actual_processors.has_key?(service_name)
+ @actual_processors[service_name]
+ else
+ raise Thrift::Exception.new("Service name not found: #{service_name}. Did you forget to call #{self.class.name}#register_processor?")
+ end
+ end
+
+ def check_type(type)
+ unless [MessageTypes::CALL, MessageTypes::ONEWAY].include?(type)
+ raise Thrift::Exception.new('This should not have happened!?')
+ end
+ end
+
+ def check_separator(name)
+ if name.count(':') < 1
+ raise Thrift::Exception.new("Service name not found in message name: #{name}. Did you forget to use a Thrift::Protocol::MultiplexedProtocol in your client?")
+ end
+ end
+ end
+
+ class StoredMessageProtocol < BaseProtocol
+
+ include ProtocolDecorator
+
+ def initialize(protocol, message_begin)
+ super(protocol)
+ @message_begin = message_begin
+ end
+
+ def read_message_begin
+ @message_begin
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/processor.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/processor.rb
new file mode 100644
index 0000000000..ce21e120ae
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/processor.rb
@@ -0,0 +1,75 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'logger'
+
+module Thrift
+ module Processor
+ def initialize(handler, logger=nil)
+ @handler = handler
+ if logger.nil?
+ @logger = Logger.new(STDERR)
+ @logger.level = Logger::WARN
+ else
+ @logger = logger
+ end
+ end
+
+ def process(iprot, oprot)
+ name, type, seqid = iprot.read_message_begin
+ if respond_to?("process_#{name}")
+ begin
+ send("process_#{name}", seqid, iprot, oprot)
+ rescue => e
+ x = ApplicationException.new(ApplicationException::INTERNAL_ERROR, 'Internal error')
+ @logger.debug "Internal error : #{e.message}\n#{e.backtrace.join("\n")}"
+ write_error(x, oprot, name, seqid)
+ end
+ true
+ else
+ iprot.skip(Types::STRUCT)
+ iprot.read_message_end
+ x = ApplicationException.new(ApplicationException::UNKNOWN_METHOD, 'Unknown function '+name)
+ write_error(x, oprot, name, seqid)
+ false
+ end
+ end
+
+ def read_args(iprot, args_class)
+ args = args_class.new
+ args.read(iprot)
+ iprot.read_message_end
+ args
+ end
+
+ def write_result(result, oprot, name, seqid)
+ oprot.write_message_begin(name, MessageTypes::REPLY, seqid)
+ result.write(oprot)
+ oprot.write_message_end
+ oprot.trans.flush
+ end
+
+ def write_error(err, oprot, name, seqid)
+ oprot.write_message_begin(name, MessageTypes::EXCEPTION, seqid)
+ err.write(oprot)
+ oprot.write_message_end
+ oprot.trans.flush
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/base_protocol.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/base_protocol.rb
new file mode 100644
index 0000000000..88f44d46df
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/base_protocol.rb
@@ -0,0 +1,379 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+# this require is to make generated struct definitions happy
+require 'set'
+
+module Thrift
+ class ProtocolException < Exception
+
+ UNKNOWN = 0
+ INVALID_DATA = 1
+ NEGATIVE_SIZE = 2
+ SIZE_LIMIT = 3
+ BAD_VERSION = 4
+ NOT_IMPLEMENTED = 5
+ DEPTH_LIMIT = 6
+
+ attr_reader :type
+
+ def initialize(type=UNKNOWN, message=nil)
+ super(message)
+ @type = type
+ end
+ end
+
+ class BaseProtocol
+
+ attr_reader :trans
+
+ def initialize(trans)
+ @trans = trans
+ end
+
+ def native?
+ puts "wrong method is being called!"
+ false
+ end
+
+ def write_message_begin(name, type, seqid)
+ raise NotImplementedError
+ end
+
+ def write_message_end; nil; end
+
+ def write_struct_begin(name)
+ raise NotImplementedError
+ end
+
+ def write_struct_end; nil; end
+
+ def write_field_begin(name, type, id)
+ raise NotImplementedError
+ end
+
+ def write_field_end; nil; end
+
+ def write_field_stop
+ raise NotImplementedError
+ end
+
+ def write_map_begin(ktype, vtype, size)
+ raise NotImplementedError
+ end
+
+ def write_map_end; nil; end
+
+ def write_list_begin(etype, size)
+ raise NotImplementedError
+ end
+
+ def write_list_end; nil; end
+
+ def write_set_begin(etype, size)
+ raise NotImplementedError
+ end
+
+ def write_set_end; nil; end
+
+ def write_bool(bool)
+ raise NotImplementedError
+ end
+
+ def write_byte(byte)
+ raise NotImplementedError
+ end
+
+ def write_i16(i16)
+ raise NotImplementedError
+ end
+
+ def write_i32(i32)
+ raise NotImplementedError
+ end
+
+ def write_i64(i64)
+ raise NotImplementedError
+ end
+
+ def write_double(dub)
+ raise NotImplementedError
+ end
+
+ # Writes a Thrift String. In Ruby 1.9+, the String passed will be transcoded to UTF-8.
+ #
+ # str - The String to write.
+ #
+ # Raises EncodingError if the transcoding to UTF-8 fails.
+ #
+ # Returns nothing.
+ def write_string(str)
+ raise NotImplementedError
+ end
+
+ # Writes a Thrift Binary (Thrift String with no encoding). In Ruby 1.9+, the String passed
+ # will forced into BINARY encoding.
+ #
+ # buf - The String to write.
+ #
+ # Returns nothing.
+ def write_binary(buf)
+ raise NotImplementedError
+ end
+
+ def read_message_begin
+ raise NotImplementedError
+ end
+
+ def read_message_end; nil; end
+
+ def read_struct_begin
+ raise NotImplementedError
+ end
+
+ def read_struct_end; nil; end
+
+ def read_field_begin
+ raise NotImplementedError
+ end
+
+ def read_field_end; nil; end
+
+ def read_map_begin
+ raise NotImplementedError
+ end
+
+ def read_map_end; nil; end
+
+ def read_list_begin
+ raise NotImplementedError
+ end
+
+ def read_list_end; nil; end
+
+ def read_set_begin
+ raise NotImplementedError
+ end
+
+ def read_set_end; nil; end
+
+ def read_bool
+ raise NotImplementedError
+ end
+
+ def read_byte
+ raise NotImplementedError
+ end
+
+ def read_i16
+ raise NotImplementedError
+ end
+
+ def read_i32
+ raise NotImplementedError
+ end
+
+ def read_i64
+ raise NotImplementedError
+ end
+
+ def read_double
+ raise NotImplementedError
+ end
+
+ # Reads a Thrift String. In Ruby 1.9+, all Strings will be returned with an Encoding of UTF-8.
+ #
+ # Returns a String.
+ def read_string
+ raise NotImplementedError
+ end
+
+ # Reads a Thrift Binary (Thrift String without encoding). In Ruby 1.9+, all Strings will be returned
+ # with an Encoding of BINARY.
+ #
+ # Returns a String.
+ def read_binary
+ raise NotImplementedError
+ end
+
+ # Writes a field based on the field information, field ID and value.
+ #
+ # field_info - A Hash containing the definition of the field:
+ # :name - The name of the field.
+ # :type - The type of the field, which must be a Thrift::Types constant.
+ # :binary - A Boolean flag that indicates if Thrift::Types::STRING is a binary string (string without encoding).
+ # fid - The ID of the field.
+ # value - The field's value to write; object type varies based on :type.
+ #
+ # Returns nothing.
+ def write_field(*args)
+ if args.size == 3
+ # handles the documented method signature - write_field(field_info, fid, value)
+ field_info = args[0]
+ fid = args[1]
+ value = args[2]
+ elsif args.size == 4
+ # handles the deprecated method signature - write_field(name, type, fid, value)
+ field_info = {:name => args[0], :type => args[1]}
+ fid = args[2]
+ value = args[3]
+ else
+ raise ArgumentError, "wrong number of arguments (#{args.size} for 3)"
+ end
+
+ write_field_begin(field_info[:name], field_info[:type], fid)
+ write_type(field_info, value)
+ write_field_end
+ end
+
+ # Writes a field value based on the field information.
+ #
+ # field_info - A Hash containing the definition of the field:
+ # :type - The Thrift::Types constant that determines how the value is written.
+ # :binary - A Boolean flag that indicates if Thrift::Types::STRING is a binary string (string without encoding).
+ # value - The field's value to write; object type varies based on field_info[:type].
+ #
+ # Returns nothing.
+ def write_type(field_info, value)
+ # if field_info is a Fixnum, assume it is a Thrift::Types constant
+ # convert it into a field_info Hash for backwards compatibility
+ if field_info.is_a? Fixnum
+ field_info = {:type => field_info}
+ end
+
+ case field_info[:type]
+ when Types::BOOL
+ write_bool(value)
+ when Types::BYTE
+ write_byte(value)
+ when Types::DOUBLE
+ write_double(value)
+ when Types::I16
+ write_i16(value)
+ when Types::I32
+ write_i32(value)
+ when Types::I64
+ write_i64(value)
+ when Types::STRING
+ if field_info[:binary]
+ write_binary(value)
+ else
+ write_string(value)
+ end
+ when Types::STRUCT
+ value.write(self)
+ else
+ raise NotImplementedError
+ end
+ end
+
+ # Reads a field value based on the field information.
+ #
+ # field_info - A Hash containing the pertinent data to write:
+ # :type - The Thrift::Types constant that determines how the value is written.
+ # :binary - A flag that indicates if Thrift::Types::STRING is a binary string (string without encoding).
+ #
+ # Returns the value read; object type varies based on field_info[:type].
+ def read_type(field_info)
+ # if field_info is a Fixnum, assume it is a Thrift::Types constant
+ # convert it into a field_info Hash for backwards compatibility
+ if field_info.is_a? Fixnum
+ field_info = {:type => field_info}
+ end
+
+ case field_info[:type]
+ when Types::BOOL
+ read_bool
+ when Types::BYTE
+ read_byte
+ when Types::DOUBLE
+ read_double
+ when Types::I16
+ read_i16
+ when Types::I32
+ read_i32
+ when Types::I64
+ read_i64
+ when Types::STRING
+ if field_info[:binary]
+ read_binary
+ else
+ read_string
+ end
+ else
+ raise NotImplementedError
+ end
+ end
+
+ def skip(type)
+ case type
+ when Types::STOP
+ nil
+ when Types::BOOL
+ read_bool
+ when Types::BYTE
+ read_byte
+ when Types::I16
+ read_i16
+ when Types::I32
+ read_i32
+ when Types::I64
+ read_i64
+ when Types::DOUBLE
+ read_double
+ when Types::STRING
+ read_string
+ when Types::STRUCT
+ read_struct_begin
+ while true
+ name, type, id = read_field_begin
+ break if type == Types::STOP
+ skip(type)
+ read_field_end
+ end
+ read_struct_end
+ when Types::MAP
+ ktype, vtype, size = read_map_begin
+ size.times do
+ skip(ktype)
+ skip(vtype)
+ end
+ read_map_end
+ when Types::SET
+ etype, size = read_set_begin
+ size.times do
+ skip(etype)
+ end
+ read_set_end
+ when Types::LIST
+ etype, size = read_list_begin
+ size.times do
+ skip(etype)
+ end
+ read_list_end
+ end
+ end
+ end
+
+ class BaseProtocolFactory
+ def get_protocol(trans)
+ raise NotImplementedError
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/binary_protocol.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/binary_protocol.rb
new file mode 100644
index 0000000000..e70b1e3a04
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/binary_protocol.rb
@@ -0,0 +1,237 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class BinaryProtocol < BaseProtocol
+ VERSION_MASK = 0xffff0000
+ VERSION_1 = 0x80010000
+ TYPE_MASK = 0x000000ff
+
+ attr_reader :strict_read, :strict_write
+
+ def initialize(trans, strict_read=true, strict_write=true)
+ super(trans)
+ @strict_read = strict_read
+ @strict_write = strict_write
+
+ # Pre-allocated read buffer for fixed-size read methods. Needs to be at least 8 bytes long for
+ # read_i64() and read_double().
+ @rbuf = Bytes.empty_byte_buffer(8)
+ end
+
+ def write_message_begin(name, type, seqid)
+ # this is necessary because we added (needed) bounds checking to
+ # write_i32, and 0x80010000 is too big for that.
+ if strict_write
+ write_i16(VERSION_1 >> 16)
+ write_i16(type)
+ write_string(name)
+ write_i32(seqid)
+ else
+ write_string(name)
+ write_byte(type)
+ write_i32(seqid)
+ end
+ end
+
+ def write_struct_begin(name); nil; end
+
+ def write_field_begin(name, type, id)
+ write_byte(type)
+ write_i16(id)
+ end
+
+ def write_field_stop
+ write_byte(Thrift::Types::STOP)
+ end
+
+ def write_map_begin(ktype, vtype, size)
+ write_byte(ktype)
+ write_byte(vtype)
+ write_i32(size)
+ end
+
+ def write_list_begin(etype, size)
+ write_byte(etype)
+ write_i32(size)
+ end
+
+ def write_set_begin(etype, size)
+ write_byte(etype)
+ write_i32(size)
+ end
+
+ def write_bool(bool)
+ write_byte(bool ? 1 : 0)
+ end
+
+ def write_byte(byte)
+ raise RangeError if byte < -2**31 || byte >= 2**32
+ trans.write([byte].pack('c'))
+ end
+
+ def write_i16(i16)
+ trans.write([i16].pack('n'))
+ end
+
+ def write_i32(i32)
+ raise RangeError if i32 < -2**31 || i32 >= 2**31
+ trans.write([i32].pack('N'))
+ end
+
+ def write_i64(i64)
+ raise RangeError if i64 < -2**63 || i64 >= 2**64
+ hi = i64 >> 32
+ lo = i64 & 0xffffffff
+ trans.write([hi, lo].pack('N2'))
+ end
+
+ def write_double(dub)
+ trans.write([dub].pack('G'))
+ end
+
+ def write_string(str)
+ buf = Bytes.convert_to_utf8_byte_buffer(str)
+ write_binary(buf)
+ end
+
+ def write_binary(buf)
+ write_i32(buf.bytesize)
+ trans.write(buf)
+ end
+
+ def read_message_begin
+ version = read_i32
+ if version < 0
+ if (version & VERSION_MASK != VERSION_1)
+ raise ProtocolException.new(ProtocolException::BAD_VERSION, 'Missing version identifier')
+ end
+ type = version & TYPE_MASK
+ name = read_string
+ seqid = read_i32
+ [name, type, seqid]
+ else
+ if strict_read
+ raise ProtocolException.new(ProtocolException::BAD_VERSION, 'No version identifier, old protocol client?')
+ end
+ name = trans.read_all(version)
+ type = read_byte
+ seqid = read_i32
+ [name, type, seqid]
+ end
+ end
+
+ def read_struct_begin; nil; end
+
+ def read_field_begin
+ type = read_byte
+ if (type == Types::STOP)
+ [nil, type, 0]
+ else
+ id = read_i16
+ [nil, type, id]
+ end
+ end
+
+ def read_map_begin
+ ktype = read_byte
+ vtype = read_byte
+ size = read_i32
+ [ktype, vtype, size]
+ end
+
+ def read_list_begin
+ etype = read_byte
+ size = read_i32
+ [etype, size]
+ end
+
+ def read_set_begin
+ etype = read_byte
+ size = read_i32
+ [etype, size]
+ end
+
+ def read_bool
+ byte = read_byte
+ byte != 0
+ end
+
+ def read_byte
+ val = trans.read_byte
+ if (val > 0x7f)
+ val = 0 - ((val - 1) ^ 0xff)
+ end
+ val
+ end
+
+ def read_i16
+ trans.read_into_buffer(@rbuf, 2)
+ val, = @rbuf.unpack('n')
+ if (val > 0x7fff)
+ val = 0 - ((val - 1) ^ 0xffff)
+ end
+ val
+ end
+
+ def read_i32
+ trans.read_into_buffer(@rbuf, 4)
+ val, = @rbuf.unpack('N')
+ if (val > 0x7fffffff)
+ val = 0 - ((val - 1) ^ 0xffffffff)
+ end
+ val
+ end
+
+ def read_i64
+ trans.read_into_buffer(@rbuf, 8)
+ hi, lo = @rbuf.unpack('N2')
+ if (hi > 0x7fffffff)
+ hi ^= 0xffffffff
+ lo ^= 0xffffffff
+ 0 - (hi << 32) - lo - 1
+ else
+ (hi << 32) + lo
+ end
+ end
+
+ def read_double
+ trans.read_into_buffer(@rbuf, 8)
+ val = @rbuf.unpack('G').first
+ val
+ end
+
+ def read_string
+ buffer = read_binary
+ Bytes.convert_to_string(buffer)
+ end
+
+ def read_binary
+ size = read_i32
+ trans.read_all(size)
+ end
+
+ end
+
+ class BinaryProtocolFactory < BaseProtocolFactory
+ def get_protocol(trans)
+ return Thrift::BinaryProtocol.new(trans)
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/binary_protocol_accelerated.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/binary_protocol_accelerated.rb
new file mode 100644
index 0000000000..70ea652c82
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/binary_protocol_accelerated.rb
@@ -0,0 +1,39 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+=begin
+The only change required for a transport to support BinaryProtocolAccelerated is to implement 2 methods:
+ * borrow(size), which takes an optional argument and returns atleast _size_ bytes from the transport,
+ or the default buffer size if no argument is given
+ * consume!(size), which removes size bytes from the front of the buffer
+
+See MemoryBuffer and BufferedTransport for examples.
+=end
+
+module Thrift
+ class BinaryProtocolAcceleratedFactory < BaseProtocolFactory
+ def get_protocol(trans)
+ if (defined? BinaryProtocolAccelerated)
+ BinaryProtocolAccelerated.new(trans)
+ else
+ BinaryProtocol.new(trans)
+ end
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/compact_protocol.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/compact_protocol.rb
new file mode 100644
index 0000000000..605eea67f0
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/compact_protocol.rb
@@ -0,0 +1,435 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class CompactProtocol < BaseProtocol
+
+ PROTOCOL_ID = [0x82].pack('c').unpack('c').first
+ VERSION = 1
+ VERSION_MASK = 0x1f
+ TYPE_MASK = 0xE0
+ TYPE_BITS = 0x07
+ TYPE_SHIFT_AMOUNT = 5
+
+ TSTOP = ["", Types::STOP, 0]
+
+ #
+ # All of the on-wire type codes.
+ #
+ class CompactTypes
+ BOOLEAN_TRUE = 0x01
+ BOOLEAN_FALSE = 0x02
+ BYTE = 0x03
+ I16 = 0x04
+ I32 = 0x05
+ I64 = 0x06
+ DOUBLE = 0x07
+ BINARY = 0x08
+ LIST = 0x09
+ SET = 0x0A
+ MAP = 0x0B
+ STRUCT = 0x0C
+
+ def self.is_bool_type?(b)
+ (b & 0x0f) == BOOLEAN_TRUE || (b & 0x0f) == BOOLEAN_FALSE
+ end
+
+ COMPACT_TO_TTYPE = {
+ Types::STOP => Types::STOP,
+ BOOLEAN_FALSE => Types::BOOL,
+ BOOLEAN_TRUE => Types::BOOL,
+ BYTE => Types::BYTE,
+ I16 => Types::I16,
+ I32 => Types::I32,
+ I64 => Types::I64,
+ DOUBLE => Types::DOUBLE,
+ BINARY => Types::STRING,
+ LIST => Types::LIST,
+ SET => Types::SET,
+ MAP => Types::MAP,
+ STRUCT => Types::STRUCT
+ }
+
+ TTYPE_TO_COMPACT = {
+ Types::STOP => Types::STOP,
+ Types::BOOL => BOOLEAN_TRUE,
+ Types::BYTE => BYTE,
+ Types::I16 => I16,
+ Types::I32 => I32,
+ Types::I64 => I64,
+ Types::DOUBLE => DOUBLE,
+ Types::STRING => BINARY,
+ Types::LIST => LIST,
+ Types::SET => SET,
+ Types::MAP => MAP,
+ Types::STRUCT => STRUCT
+ }
+
+ def self.get_ttype(compact_type)
+ val = COMPACT_TO_TTYPE[compact_type & 0x0f]
+ raise "don't know what type: #{compact_type & 0x0f}" unless val
+ val
+ end
+
+ def self.get_compact_type(ttype)
+ val = TTYPE_TO_COMPACT[ttype]
+ raise "don't know what type: #{ttype & 0x0f}" unless val
+ val
+ end
+ end
+
+ def initialize(transport)
+ super(transport)
+
+ @last_field = [0]
+ @boolean_value = nil
+
+ # Pre-allocated read buffer for read_double().
+ @rbuf = Bytes.empty_byte_buffer(8)
+ end
+
+ def write_message_begin(name, type, seqid)
+ write_byte(PROTOCOL_ID)
+ write_byte((VERSION & VERSION_MASK) | ((type << TYPE_SHIFT_AMOUNT) & TYPE_MASK))
+ write_varint32(seqid)
+ write_string(name)
+ nil
+ end
+
+ def write_struct_begin(name)
+ @last_field.push(0)
+ nil
+ end
+
+ def write_struct_end
+ @last_field.pop
+ nil
+ end
+
+ def write_field_begin(name, type, id)
+ if type == Types::BOOL
+ # we want to possibly include the value, so we'll wait.
+ @boolean_field = [type, id]
+ else
+ write_field_begin_internal(type, id)
+ end
+ nil
+ end
+
+ #
+ # The workhorse of writeFieldBegin. It has the option of doing a
+ # 'type override' of the type header. This is used specifically in the
+ # boolean field case.
+ #
+ def write_field_begin_internal(type, id, type_override=nil)
+ last_id = @last_field.pop
+
+ # if there's a type override, use that.
+ typeToWrite = type_override || CompactTypes.get_compact_type(type)
+
+ # check if we can use delta encoding for the field id
+ if id > last_id && id - last_id <= 15
+ # write them together
+ write_byte((id - last_id) << 4 | typeToWrite)
+ else
+ # write them separate
+ write_byte(typeToWrite)
+ write_i16(id)
+ end
+
+ @last_field.push(id)
+ nil
+ end
+
+ def write_field_stop
+ write_byte(Types::STOP)
+ end
+
+ def write_map_begin(ktype, vtype, size)
+ if (size == 0)
+ write_byte(0)
+ else
+ write_varint32(size)
+ write_byte(CompactTypes.get_compact_type(ktype) << 4 | CompactTypes.get_compact_type(vtype))
+ end
+ end
+
+ def write_list_begin(etype, size)
+ write_collection_begin(etype, size)
+ end
+
+ def write_set_begin(etype, size)
+ write_collection_begin(etype, size);
+ end
+
+ def write_bool(bool)
+ type = bool ? CompactTypes::BOOLEAN_TRUE : CompactTypes::BOOLEAN_FALSE
+ unless @boolean_field.nil?
+ # we haven't written the field header yet
+ write_field_begin_internal(@boolean_field.first, @boolean_field.last, type)
+ @boolean_field = nil
+ else
+ # we're not part of a field, so just write the value.
+ write_byte(type)
+ end
+ end
+
+ def write_byte(byte)
+ @trans.write([byte].pack('c'))
+ end
+
+ def write_i16(i16)
+ write_varint32(int_to_zig_zag(i16))
+ end
+
+ def write_i32(i32)
+ write_varint32(int_to_zig_zag(i32))
+ end
+
+ def write_i64(i64)
+ write_varint64(long_to_zig_zag(i64))
+ end
+
+ def write_double(dub)
+ @trans.write([dub].pack("G").reverse)
+ end
+
+ def write_string(str)
+ buf = Bytes.convert_to_utf8_byte_buffer(str)
+ write_binary(buf)
+ end
+
+ def write_binary(buf)
+ write_varint32(buf.bytesize)
+ @trans.write(buf)
+ end
+
+ def read_message_begin
+ protocol_id = read_byte()
+ if protocol_id != PROTOCOL_ID
+ raise ProtocolException.new("Expected protocol id #{PROTOCOL_ID} but got #{protocol_id}")
+ end
+
+ version_and_type = read_byte()
+ version = version_and_type & VERSION_MASK
+ if (version != VERSION)
+ raise ProtocolException.new("Expected version #{VERSION} but got #{version}");
+ end
+
+ type = (version_and_type >> TYPE_SHIFT_AMOUNT) & TYPE_BITS
+ seqid = read_varint32()
+ messageName = read_string()
+ [messageName, type, seqid]
+ end
+
+ def read_struct_begin
+ @last_field.push(0)
+ ""
+ end
+
+ def read_struct_end
+ @last_field.pop()
+ nil
+ end
+
+ def read_field_begin
+ type = read_byte()
+
+ # if it's a stop, then we can return immediately, as the struct is over.
+ if (type & 0x0f) == Types::STOP
+ TSTOP
+ else
+ field_id = nil
+
+ # mask off the 4 MSB of the type header. it could contain a field id delta.
+ modifier = (type & 0xf0) >> 4
+ if modifier == 0
+ # not a delta. look ahead for the zigzag varint field id.
+ @last_field.pop
+ field_id = read_i16()
+ else
+ # has a delta. add the delta to the last read field id.
+ field_id = @last_field.pop + modifier
+ end
+
+ # if this happens to be a boolean field, the value is encoded in the type
+ if CompactTypes.is_bool_type?(type)
+ # save the boolean value in a special instance variable.
+ @bool_value = (type & 0x0f) == CompactTypes::BOOLEAN_TRUE
+ end
+
+ # push the new field onto the field stack so we can keep the deltas going.
+ @last_field.push(field_id)
+ ["", CompactTypes.get_ttype(type & 0x0f), field_id]
+ end
+ end
+
+ def read_map_begin
+ size = read_varint32()
+ key_and_value_type = size == 0 ? 0 : read_byte()
+ [CompactTypes.get_ttype(key_and_value_type >> 4), CompactTypes.get_ttype(key_and_value_type & 0xf), size]
+ end
+
+ def read_list_begin
+ size_and_type = read_byte()
+ size = (size_and_type >> 4) & 0x0f
+ if size == 15
+ size = read_varint32()
+ end
+ type = CompactTypes.get_ttype(size_and_type)
+ [type, size]
+ end
+
+ def read_set_begin
+ read_list_begin
+ end
+
+ def read_bool
+ unless @bool_value.nil?
+ bv = @bool_value
+ @bool_value = nil
+ bv
+ else
+ read_byte() == CompactTypes::BOOLEAN_TRUE
+ end
+ end
+
+ def read_byte
+ val = trans.read_byte
+ if (val > 0x7f)
+ val = 0 - ((val - 1) ^ 0xff)
+ end
+ val
+ end
+
+ def read_i16
+ zig_zag_to_int(read_varint32())
+ end
+
+ def read_i32
+ zig_zag_to_int(read_varint32())
+ end
+
+ def read_i64
+ zig_zag_to_long(read_varint64())
+ end
+
+ def read_double
+ trans.read_into_buffer(@rbuf, 8)
+ val = @rbuf.reverse.unpack('G').first
+ val
+ end
+
+ def read_string
+ buffer = read_binary
+ Bytes.convert_to_string(buffer)
+ end
+
+ def read_binary
+ size = read_varint32()
+ trans.read_all(size)
+ end
+
+ private
+
+ #
+ # Abstract method for writing the start of lists and sets. List and sets on
+ # the wire differ only by the type indicator.
+ #
+ def write_collection_begin(elem_type, size)
+ if size <= 14
+ write_byte(size << 4 | CompactTypes.get_compact_type(elem_type))
+ else
+ write_byte(0xf0 | CompactTypes.get_compact_type(elem_type))
+ write_varint32(size)
+ end
+ end
+
+ def write_varint32(n)
+ # int idx = 0;
+ while true
+ if (n & ~0x7F) == 0
+ # i32buf[idx++] = (byte)n;
+ write_byte(n)
+ break
+ # return;
+ else
+ # i32buf[idx++] = (byte)((n & 0x7F) | 0x80);
+ write_byte((n & 0x7F) | 0x80)
+ n = n >> 7
+ end
+ end
+ # trans_.write(i32buf, 0, idx);
+ end
+
+ SEVEN_BIT_MASK = 0x7F
+ EVERYTHING_ELSE_MASK = ~SEVEN_BIT_MASK
+
+ def write_varint64(n)
+ while true
+ if (n & EVERYTHING_ELSE_MASK) == 0 #TODO need to find a way to make this into a long...
+ write_byte(n)
+ break
+ else
+ write_byte((n & SEVEN_BIT_MASK) | 0x80)
+ n >>= 7
+ end
+ end
+ end
+
+ def read_varint32()
+ read_varint64()
+ end
+
+ def read_varint64()
+ shift = 0
+ result = 0
+ while true
+ b = read_byte()
+ result |= (b & 0x7f) << shift
+ break if (b & 0x80) != 0x80
+ shift += 7
+ end
+ result
+ end
+
+ def int_to_zig_zag(n)
+ (n << 1) ^ (n >> 31)
+ end
+
+ def long_to_zig_zag(l)
+ # puts "zz encoded #{l} to #{(l << 1) ^ (l >> 63)}"
+ (l << 1) ^ (l >> 63)
+ end
+
+ def zig_zag_to_int(n)
+ (n >> 1) ^ -(n & 1)
+ end
+
+ def zig_zag_to_long(n)
+ (n >> 1) ^ -(n & 1)
+ end
+ end
+
+ class CompactProtocolFactory < BaseProtocolFactory
+ def get_protocol(trans)
+ CompactProtocol.new(trans)
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/json_protocol.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/json_protocol.rb
new file mode 100644
index 0000000000..514bdbf6fb
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/json_protocol.rb
@@ -0,0 +1,778 @@
+# encoding: UTF-8
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'base64'
+
+module Thrift
+ class LookaheadReader
+ def initialize(trans)
+ @trans = trans
+ @hasData = false
+ @data = nil
+ end
+
+ def read
+ if @hasData
+ @hasData = false
+ else
+ @data = @trans.read(1)
+ end
+
+ return @data
+ end
+
+ def peek
+ if !@hasData
+ @data = @trans.read(1)
+ end
+ @hasData = true
+ return @data
+ end
+ end
+
+ #
+ # Class to serve as base JSON context and as base class for other context
+ # implementations
+ #
+ class JSONContext
+ @@kJSONElemSeparator = ','
+ #
+ # Write context data to the trans. Default is to do nothing.
+ #
+ def write(trans)
+ end
+
+ #
+ # Read context data from the trans. Default is to do nothing.
+ #
+ def read(reader)
+ end
+
+ #
+ # Return true if numbers need to be escaped as strings in this context.
+ # Default behavior is to return false.
+ #
+ def escapeNum
+ return false
+ end
+ end
+
+ # Context class for object member key-value pairs
+ class JSONPairContext < JSONContext
+ @@kJSONPairSeparator = ':'
+
+ def initialize
+ @first = true
+ @colon = true
+ end
+
+ def write(trans)
+ if (@first)
+ @first = false
+ @colon = true
+ else
+ trans.write(@colon ? @@kJSONPairSeparator : @@kJSONElemSeparator)
+ @colon = !@colon
+ end
+ end
+
+ def read(reader)
+ if (@first)
+ @first = false
+ @colon = true
+ else
+ ch = (@colon ? @@kJSONPairSeparator : @@kJSONElemSeparator)
+ @colon = !@colon
+ JsonProtocol::read_syntax_char(reader, ch)
+ end
+ end
+
+ # Numbers must be turned into strings if they are the key part of a pair
+ def escapeNum
+ return @colon
+ end
+ end
+
+ # Context class for lists
+ class JSONListContext < JSONContext
+
+ def initialize
+ @first = true
+ end
+
+ def write(trans)
+ if (@first)
+ @first = false
+ else
+ trans.write(@@kJSONElemSeparator)
+ end
+ end
+
+ def read(reader)
+ if (@first)
+ @first = false
+ else
+ JsonProtocol::read_syntax_char(reader, @@kJSONElemSeparator)
+ end
+ end
+ end
+
+ class JsonProtocol < BaseProtocol
+
+ @@kJSONObjectStart = '{'
+ @@kJSONObjectEnd = '}'
+ @@kJSONArrayStart = '['
+ @@kJSONArrayEnd = ']'
+ @@kJSONNewline = '\n'
+ @@kJSONBackslash = '\\'
+ @@kJSONStringDelimiter = '"'
+
+ @@kThriftVersion1 = 1
+
+ @@kThriftNan = "NaN"
+ @@kThriftInfinity = "Infinity"
+ @@kThriftNegativeInfinity = "-Infinity"
+
+ def initialize(trans)
+ super(trans)
+ @context = JSONContext.new
+ @contexts = Array.new
+ @reader = LookaheadReader.new(trans)
+ end
+
+ def get_type_name_for_type_id(id)
+ case id
+ when Types::BOOL
+ "tf"
+ when Types::BYTE
+ "i8"
+ when Types::I16
+ "i16"
+ when Types::I32
+ "i32"
+ when Types::I64
+ "i64"
+ when Types::DOUBLE
+ "dbl"
+ when Types::STRING
+ "str"
+ when Types::STRUCT
+ "rec"
+ when Types::MAP
+ "map"
+ when Types::SET
+ "set"
+ when Types::LIST
+ "lst"
+ else
+ raise NotImplementedError
+ end
+ end
+
+ def get_type_id_for_type_name(name)
+ if (name == "tf")
+ result = Types::BOOL
+ elsif (name == "i8")
+ result = Types::BYTE
+ elsif (name == "i16")
+ result = Types::I16
+ elsif (name == "i32")
+ result = Types::I32
+ elsif (name == "i64")
+ result = Types::I64
+ elsif (name == "dbl")
+ result = Types::DOUBLE
+ elsif (name == "str")
+ result = Types::STRING
+ elsif (name == "rec")
+ result = Types::STRUCT
+ elsif (name == "map")
+ result = Types::MAP
+ elsif (name == "set")
+ result = Types::SET
+ elsif (name == "lst")
+ result = Types::LIST
+ else
+ result = Types::STOP
+ end
+ if (result == Types::STOP)
+ raise NotImplementedError
+ end
+ return result
+ end
+
+ # Static helper functions
+
+ # Read 1 character from the trans and verify that it is the expected character ch.
+ # Throw a protocol exception if it is not.
+ def self.read_syntax_char(reader, ch)
+ ch2 = reader.read
+ if (ch2 != ch)
+ raise ProtocolException.new(ProtocolException::INVALID_DATA, "Expected \'#{ch}\' got \'#{ch2}\'.")
+ end
+ end
+
+ # Return true if the character ch is in [-+0-9.Ee]; false otherwise
+ def is_json_numeric(ch)
+ case ch
+ when '+', '-', '.', '0' .. '9', 'E', "e"
+ return true
+ else
+ return false
+ end
+ end
+
+ def push_context(context)
+ @contexts.push(@context)
+ @context = context
+ end
+
+ def pop_context
+ @context = @contexts.pop
+ end
+
+ # Write the character ch as a JSON escape sequence ("\u00xx")
+ def write_json_escape_char(ch)
+ trans.write('\\u')
+ ch_value = ch[0]
+ if (ch_value.kind_of? String)
+ ch_value = ch.bytes.first
+ end
+ trans.write(ch_value.to_s(16).rjust(4,'0'))
+ end
+
+ # Write the character ch as part of a JSON string, escaping as appropriate.
+ def write_json_char(ch)
+ # This table describes the handling for the first 0x30 characters
+ # 0 : escape using "\u00xx" notation
+ # 1 : just output index
+ # : escape using "\" notation
+ kJSONCharTable = [
+ # 0 1 2 3 4 5 6 7 8 9 A B C D E F
+ 0, 0, 0, 0, 0, 0, 0, 0,'b','t','n', 0,'f','r', 0, 0, # 0
+ 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, # 1
+ 1, 1,'"', 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, # 2
+ ]
+
+ ch_value = ch[0]
+ if (ch_value.kind_of? String)
+ ch_value = ch.bytes.first
+ end
+ if (ch_value >= 0x30)
+ if (ch == @@kJSONBackslash) # Only special character >= 0x30 is '\'
+ trans.write(@@kJSONBackslash)
+ trans.write(@@kJSONBackslash)
+ else
+ trans.write(ch)
+ end
+ else
+ outCh = kJSONCharTable[ch_value];
+ # Check if regular character, backslash escaped, or JSON escaped
+ if outCh.kind_of? String
+ trans.write(@@kJSONBackslash)
+ trans.write(outCh)
+ elsif outCh == 1
+ trans.write(ch)
+ else
+ write_json_escape_char(ch)
+ end
+ end
+ end
+
+ # Write out the contents of the string str as a JSON string, escaping characters as appropriate.
+ def write_json_string(str)
+ @context.write(trans)
+ trans.write(@@kJSONStringDelimiter)
+ str.split('').each do |ch|
+ write_json_char(ch)
+ end
+ trans.write(@@kJSONStringDelimiter)
+ end
+
+ # Write out the contents of the string as JSON string, base64-encoding
+ # the string's contents, and escaping as appropriate
+ def write_json_base64(str)
+ @context.write(trans)
+ trans.write(@@kJSONStringDelimiter)
+ trans.write(Base64.strict_encode64(str))
+ trans.write(@@kJSONStringDelimiter)
+ end
+
+ # Convert the given integer type to a JSON number, or a string
+ # if the context requires it (eg: key in a map pair).
+ def write_json_integer(num)
+ @context.write(trans)
+ escapeNum = @context.escapeNum
+ if (escapeNum)
+ trans.write(@@kJSONStringDelimiter)
+ end
+ trans.write(num.to_s);
+ if (escapeNum)
+ trans.write(@@kJSONStringDelimiter)
+ end
+ end
+
+ # Convert the given double to a JSON string, which is either the number,
+ # "NaN" or "Infinity" or "-Infinity".
+ def write_json_double(num)
+ @context.write(trans)
+ # Normalize output of thrift::to_string for NaNs and Infinities
+ special = false;
+ if (num.nan?)
+ special = true;
+ val = @@kThriftNan;
+ elsif (num.infinite?)
+ special = true;
+ val = @@kThriftInfinity;
+ if (num < 0.0)
+ val = @@kThriftNegativeInfinity;
+ end
+ else
+ val = num.to_s
+ end
+
+ escapeNum = special || @context.escapeNum
+ if (escapeNum)
+ trans.write(@@kJSONStringDelimiter)
+ end
+ trans.write(val)
+ if (escapeNum)
+ trans.write(@@kJSONStringDelimiter)
+ end
+ end
+
+ def write_json_object_start
+ @context.write(trans)
+ trans.write(@@kJSONObjectStart)
+ push_context(JSONPairContext.new);
+ end
+
+ def write_json_object_end
+ pop_context
+ trans.write(@@kJSONObjectEnd)
+ end
+
+ def write_json_array_start
+ @context.write(trans)
+ trans.write(@@kJSONArrayStart)
+ push_context(JSONListContext.new);
+ end
+
+ def write_json_array_end
+ pop_context
+ trans.write(@@kJSONArrayEnd)
+ end
+
+ def write_message_begin(name, type, seqid)
+ write_json_array_start
+ write_json_integer(@@kThriftVersion1)
+ write_json_string(name)
+ write_json_integer(type)
+ write_json_integer(seqid)
+ end
+
+ def write_message_end
+ write_json_array_end
+ end
+
+ def write_struct_begin(name)
+ write_json_object_start
+ end
+
+ def write_struct_end
+ write_json_object_end
+ end
+
+ def write_field_begin(name, type, id)
+ write_json_integer(id)
+ write_json_object_start
+ write_json_string(get_type_name_for_type_id(type))
+ end
+
+ def write_field_end
+ write_json_object_end
+ end
+
+ def write_field_stop; nil; end
+
+ def write_map_begin(ktype, vtype, size)
+ write_json_array_start
+ write_json_string(get_type_name_for_type_id(ktype))
+ write_json_string(get_type_name_for_type_id(vtype))
+ write_json_integer(size)
+ write_json_object_start
+ end
+
+ def write_map_end
+ write_json_object_end
+ write_json_array_end
+ end
+
+ def write_list_begin(etype, size)
+ write_json_array_start
+ write_json_string(get_type_name_for_type_id(etype))
+ write_json_integer(size)
+ end
+
+ def write_list_end
+ write_json_array_end
+ end
+
+ def write_set_begin(etype, size)
+ write_json_array_start
+ write_json_string(get_type_name_for_type_id(etype))
+ write_json_integer(size)
+ end
+
+ def write_set_end
+ write_json_array_end
+ end
+
+ def write_bool(bool)
+ write_json_integer(bool ? 1 : 0)
+ end
+
+ def write_byte(byte)
+ write_json_integer(byte)
+ end
+
+ def write_i16(i16)
+ write_json_integer(i16)
+ end
+
+ def write_i32(i32)
+ write_json_integer(i32)
+ end
+
+ def write_i64(i64)
+ write_json_integer(i64)
+ end
+
+ def write_double(dub)
+ write_json_double(dub)
+ end
+
+ def write_string(str)
+ write_json_string(str)
+ end
+
+ def write_binary(str)
+ write_json_base64(str)
+ end
+
+ ##
+ # Reading functions
+ ##
+
+ # Reads 1 byte and verifies that it matches ch.
+ def read_json_syntax_char(ch)
+ JsonProtocol::read_syntax_char(@reader, ch)
+ end
+
+ # Decodes the four hex parts of a JSON escaped string character and returns
+ # the character via out.
+ #
+ # Note - this only supports Unicode characters in the BMP (U+0000 to U+FFFF);
+ # characters above the BMP are encoded as two escape sequences (surrogate pairs),
+ # which is not yet implemented
+ def read_json_escape_char
+ str = @reader.read
+ str += @reader.read
+ str += @reader.read
+ str += @reader.read
+ if RUBY_VERSION >= '1.9'
+ str.hex.chr(Encoding::UTF_8)
+ else
+ str.hex.chr
+ end
+ end
+
+ # Decodes a JSON string, including unescaping, and returns the string via str
+ def read_json_string(skipContext = false)
+ # This string's characters must match up with the elements in escape_char_vals.
+ # I don't have '/' on this list even though it appears on www.json.org --
+ # it is not in the RFC -> it is. See RFC 4627
+ escape_chars = "\"\\/bfnrt"
+
+ # The elements of this array must match up with the sequence of characters in
+ # escape_chars
+ escape_char_vals = [
+ "\"", "\\", "\/", "\b", "\f", "\n", "\r", "\t",
+ ]
+
+ if !skipContext
+ @context.read(@reader)
+ end
+ read_json_syntax_char(@@kJSONStringDelimiter)
+ ch = ""
+ str = ""
+ while (true)
+ ch = @reader.read
+ if (ch == @@kJSONStringDelimiter)
+ break
+ end
+ if (ch == @@kJSONBackslash)
+ ch = @reader.read
+ if (ch == 'u')
+ ch = read_json_escape_char
+ else
+ pos = escape_chars.index(ch);
+ if (pos.nil?) # not found
+ raise ProtocolException.new(ProtocolException::INVALID_DATA, "Expected control char, got \'#{ch}\'.")
+ end
+ ch = escape_char_vals[pos]
+ end
+ end
+ str += ch
+ end
+ return str
+ end
+
+ # Reads a block of base64 characters, decoding it, and returns via str
+ def read_json_base64
+ str = read_json_string
+ m = str.length % 4
+ if m != 0
+ # Add missing padding
+ (4 - m).times do
+ str += '='
+ end
+ end
+ Base64.strict_decode64(str)
+ end
+
+ # Reads a sequence of characters, stopping at the first one that is not
+ # a valid JSON numeric character.
+ def read_json_numeric_chars
+ str = ""
+ while (true)
+ ch = @reader.peek
+ if (!is_json_numeric(ch))
+ break;
+ end
+ ch = @reader.read
+ str += ch
+ end
+ return str
+ end
+
+ # Reads a sequence of characters and assembles them into a number,
+ # returning them via num
+ def read_json_integer
+ @context.read(@reader)
+ if (@context.escapeNum)
+ read_json_syntax_char(@@kJSONStringDelimiter)
+ end
+ str = read_json_numeric_chars
+
+ begin
+ num = Integer(str);
+ rescue
+ raise ProtocolException.new(ProtocolException::INVALID_DATA, "Expected numeric value; got \"#{str}\"")
+ end
+
+ if (@context.escapeNum)
+ read_json_syntax_char(@@kJSONStringDelimiter)
+ end
+
+ return num
+ end
+
+ # Reads a JSON number or string and interprets it as a double.
+ def read_json_double
+ @context.read(@reader)
+ num = 0
+ if (@reader.peek == @@kJSONStringDelimiter)
+ str = read_json_string(true)
+ # Check for NaN, Infinity and -Infinity
+ if (str == @@kThriftNan)
+ num = (+1.0/0.0)/(+1.0/0.0)
+ elsif (str == @@kThriftInfinity)
+ num = +1.0/0.0
+ elsif (str == @@kThriftNegativeInfinity)
+ num = -1.0/0.0
+ else
+ if (!@context.escapeNum)
+ # Raise exception -- we should not be in a string in this case
+ raise ProtocolException.new(ProtocolException::INVALID_DATA, "Numeric data unexpectedly quoted")
+ end
+ begin
+ num = Float(str)
+ rescue
+ raise ProtocolException.new(ProtocolException::INVALID_DATA, "Expected numeric value; got \"#{str}\"")
+ end
+ end
+ else
+ if (@context.escapeNum)
+ # This will throw - we should have had a quote if escapeNum == true
+ read_json_syntax_char(@@kJSONStringDelimiter)
+ end
+ str = read_json_numeric_chars
+ begin
+ num = Float(str)
+ rescue
+ raise ProtocolException.new(ProtocolException::INVALID_DATA, "Expected numeric value; got \"#{str}\"")
+ end
+ end
+ return num
+ end
+
+ def read_json_object_start
+ @context.read(@reader)
+ read_json_syntax_char(@@kJSONObjectStart)
+ push_context(JSONPairContext.new)
+ nil
+ end
+
+ def read_json_object_end
+ read_json_syntax_char(@@kJSONObjectEnd)
+ pop_context
+ nil
+ end
+
+ def read_json_array_start
+ @context.read(@reader)
+ read_json_syntax_char(@@kJSONArrayStart)
+ push_context(JSONListContext.new)
+ nil
+ end
+
+ def read_json_array_end
+ read_json_syntax_char(@@kJSONArrayEnd)
+ pop_context
+ nil
+ end
+
+ def read_message_begin
+ read_json_array_start
+ version = read_json_integer
+ if (version != @@kThriftVersion1)
+ raise ProtocolException.new(ProtocolException::BAD_VERSION, 'Message contained bad version.')
+ end
+ name = read_json_string
+ message_type = read_json_integer
+ seqid = read_json_integer
+ [name, message_type, seqid]
+ end
+
+ def read_message_end
+ read_json_array_end
+ nil
+ end
+
+ def read_struct_begin
+ read_json_object_start
+ nil
+ end
+
+ def read_struct_end
+ read_json_object_end
+ nil
+ end
+
+ def read_field_begin
+ # Check if we hit the end of the list
+ ch = @reader.peek
+ if (ch == @@kJSONObjectEnd)
+ field_type = Types::STOP
+ else
+ field_id = read_json_integer
+ read_json_object_start
+ field_type = get_type_id_for_type_name(read_json_string)
+ end
+ [nil, field_type, field_id]
+ end
+
+ def read_field_end
+ read_json_object_end
+ end
+
+ def read_map_begin
+ read_json_array_start
+ key_type = get_type_id_for_type_name(read_json_string)
+ val_type = get_type_id_for_type_name(read_json_string)
+ size = read_json_integer
+ read_json_object_start
+ [key_type, val_type, size]
+ end
+
+ def read_map_end
+ read_json_object_end
+ read_json_array_end
+ end
+
+ def read_list_begin
+ read_json_array_start
+ [get_type_id_for_type_name(read_json_string), read_json_integer]
+ end
+
+ def read_list_end
+ read_json_array_end
+ end
+
+ def read_set_begin
+ read_json_array_start
+ [get_type_id_for_type_name(read_json_string), read_json_integer]
+ end
+
+ def read_set_end
+ read_json_array_end
+ end
+
+ def read_bool
+ byte = read_byte
+ byte != 0
+ end
+
+ def read_byte
+ read_json_integer
+ end
+
+ def read_i16
+ read_json_integer
+ end
+
+ def read_i32
+ read_json_integer
+ end
+
+ def read_i64
+ read_json_integer
+ end
+
+ def read_double
+ read_json_double
+ end
+
+ def read_string
+ read_json_string
+ end
+
+ def read_binary
+ read_json_base64
+ end
+ end
+
+ class JsonProtocolFactory < BaseProtocolFactory
+ def get_protocol(trans)
+ return Thrift::JsonProtocol.new(trans)
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/multiplexed_protocol.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/multiplexed_protocol.rb
new file mode 100644
index 0000000000..13c9d93e16
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/multiplexed_protocol.rb
@@ -0,0 +1,40 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+
+require 'thrift/protocol/protocol_decorator'
+
+module Thrift
+ class MultiplexedProtocol < BaseProtocol
+
+ include ProtocolDecorator
+
+ def initialize(protocol, service_name)
+ super(protocol)
+ @service_name = service_name
+ end
+
+ def write_message_begin(name, type, seqid)
+ case type
+ when MessageTypes::CALL, MessageTypes::ONEWAY
+ @protocol.write_message_begin("#{@service_name}:#{name}", type, seqid)
+ else
+ @protocol.write_message_begin(name, type, seqid)
+ end
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/protocol_decorator.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/protocol_decorator.rb
new file mode 100644
index 0000000000..b1e3c155d4
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/protocol/protocol_decorator.rb
@@ -0,0 +1,194 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+
+module Thrift
+ module ProtocolDecorator
+
+ def initialize(protocol)
+ @protocol = protocol
+ end
+
+ def trans
+ @protocol.trans
+ end
+
+ def write_message_begin(name, type, seqid)
+ @protocol.write_message_begin
+ end
+
+ def write_message_end
+ @protocol.write_message_end
+ end
+
+ def write_struct_begin(name)
+ @protocol.write_struct_begin(name)
+ end
+
+ def write_struct_end
+ @protocol.write_struct_end
+ end
+
+ def write_field_begin(name, type, id)
+ @protocol.write_field_begin(name, type, id)
+ end
+
+ def write_field_end
+ @protocol.write_field_end
+ end
+
+ def write_field_stop
+ @protocol.write_field_stop
+ end
+
+ def write_map_begin(ktype, vtype, size)
+ @protocol.write_map_begin(ktype, vtype, size)
+ end
+
+ def write_map_end
+ @protocol.write_map_end
+ end
+
+ def write_list_begin(etype, size)
+ @protocol.write_list_begin(etype, size)
+ end
+
+ def write_list_end
+ @protocol.write_list_end
+ end
+
+ def write_set_begin(etype, size)
+ @protocol.write_set_begin(etype, size)
+ end
+
+ def write_set_end
+ @protocol.write_set_end
+ end
+
+ def write_bool(bool)
+ @protocol.write_bool(bool)
+ end
+
+ def write_byte(byte)
+ @protocol.write_byte(byte)
+ end
+
+ def write_i16(i16)
+ @protocol.write_i16(i16)
+ end
+
+ def write_i32(i32)
+ @protocol.write_i32(i32)
+ end
+
+ def write_i64(i64)
+ @protocol.write_i64(i64)
+ end
+
+ def write_double(dub)
+ @protocol.write_double(dub)
+ end
+
+ def write_string(str)
+ @protocol.write_string(str)
+ end
+
+ def write_binary(buf)
+ @protocol.write_binary(buf)
+ end
+
+ def read_message_begin
+ @protocol.read_message_begin
+ end
+
+ def read_message_end
+ @protocol.read_message_end
+ end
+
+ def read_struct_begin
+ @protocol.read_struct_begin
+ end
+
+ def read_struct_end
+ @protocol.read_struct_end
+ end
+
+ def read_field_begin
+ @protocol.read_field_begin
+ end
+
+ def read_field_end
+ @protocol.read_field_end
+ end
+
+ def read_map_begin
+ @protocol.read_map_begin
+ end
+
+ def read_map_end
+ @protocol.read_map_end
+ end
+
+ def read_list_begin
+ @protocol.read_list_begin
+ end
+
+ def read_list_end
+ @protocol.read_list_end
+ end
+
+ def read_set_begin
+ @protocol.read_set_begin
+ end
+
+ def read_set_end
+ @protocol.read_set_end
+ end
+
+ def read_bool
+ @protocol.read_bool
+ end
+
+ def read_byte
+ @protocol.read_byte
+ end
+
+ def read_i16
+ @protocol.read_i16
+ end
+
+ def read_i32
+ @protocol.read_i32
+ end
+
+ def read_i64
+ @protocol.read_i64
+ end
+
+ def read_double
+ @protocol.read_double
+ end
+
+ def read_string
+ @protocol.read_string
+ end
+
+ def read_binary
+ @protocol.read_binary
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/serializer/deserializer.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/serializer/deserializer.rb
new file mode 100644
index 0000000000..d2ee325a5c
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/serializer/deserializer.rb
@@ -0,0 +1,33 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class Deserializer
+ def initialize(protocol_factory = BinaryProtocolFactory.new)
+ @transport = MemoryBufferTransport.new
+ @protocol = protocol_factory.get_protocol(@transport)
+ end
+
+ def deserialize(base, buffer)
+ @transport.reset_buffer(buffer)
+ base.read(@protocol)
+ base
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/serializer/serializer.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/serializer/serializer.rb
new file mode 100644
index 0000000000..22316395d3
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/serializer/serializer.rb
@@ -0,0 +1,34 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class Serializer
+ def initialize(protocol_factory = BinaryProtocolFactory.new)
+ @transport = MemoryBufferTransport.new
+ @protocol = protocol_factory.get_protocol(@transport)
+ end
+
+ def serialize(base)
+ @transport.reset_buffer
+ base.write(@protocol)
+ @transport.read(@transport.available)
+ end
+ end
+end
+
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/base_server.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/base_server.rb
new file mode 100644
index 0000000000..1ee1213335
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/base_server.rb
@@ -0,0 +1,31 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class BaseServer
+ def initialize(processor, server_transport, transport_factory=nil, protocol_factory=nil)
+ @processor = processor
+ @server_transport = server_transport
+ @transport_factory = transport_factory ? transport_factory : Thrift::BaseTransportFactory.new
+ @protocol_factory = protocol_factory ? protocol_factory : Thrift::BinaryProtocolFactory.new
+ end
+
+ def serve; nil; end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/mongrel_http_server.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/mongrel_http_server.rb
new file mode 100644
index 0000000000..de354c8f93
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/mongrel_http_server.rb
@@ -0,0 +1,60 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'mongrel'
+
+## Sticks a service on a URL, using mongrel to do the HTTP work
+# DEPRECATED: Please use Thrift::ThinHTTPServer instead.
+module Thrift
+ class MongrelHTTPServer < BaseServer
+ class Handler < Mongrel::HttpHandler
+ def initialize(processor, protocol_factory)
+ @processor = processor
+ @protocol_factory = protocol_factory
+ end
+
+ def process(request, response)
+ if request.params["REQUEST_METHOD"] == "POST"
+ response.start(200) do |head, out|
+ head["Content-Type"] = "application/x-thrift"
+ transport = IOStreamTransport.new request.body, out
+ protocol = @protocol_factory.get_protocol transport
+ @processor.process protocol, protocol
+ end
+ else
+ response.start(404) { }
+ end
+ end
+ end
+
+ def initialize(processor, opts={})
+ Kernel.warn "[DEPRECATION WARNING] `Thrift::MongrelHTTPServer` is deprecated. Please use `Thrift::ThinHTTPServer` instead."
+ port = opts[:port] || 80
+ ip = opts[:ip] || "0.0.0.0"
+ path = opts[:path] || ""
+ protocol_factory = opts[:protocol_factory] || BinaryProtocolFactory.new
+ @server = Mongrel::HttpServer.new ip, port
+ @server.register "/#{path}", Handler.new(processor, protocol_factory)
+ end
+
+ def serve
+ @server.run.join
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/nonblocking_server.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/nonblocking_server.rb
new file mode 100644
index 0000000000..740f3417e2
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/nonblocking_server.rb
@@ -0,0 +1,305 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'logger'
+require 'thread'
+
+module Thrift
+ # this class expects to always use a FramedTransport for reading messages
+ class NonblockingServer < BaseServer
+ def initialize(processor, server_transport, transport_factory=nil, protocol_factory=nil, num=20, logger=nil)
+ super(processor, server_transport, transport_factory, protocol_factory)
+ @num_threads = num
+ if logger.nil?
+ @logger = Logger.new(STDERR)
+ @logger.level = Logger::WARN
+ else
+ @logger = logger
+ end
+ @shutdown_semaphore = Mutex.new
+ @transport_semaphore = Mutex.new
+ end
+
+ def serve
+ @logger.info "Starting #{self}"
+ @server_transport.listen
+ @io_manager = start_io_manager
+
+ begin
+ loop do
+ break if @server_transport.closed?
+ begin
+ rd, = select([@server_transport], nil, nil, 0.1)
+ rescue Errno::EBADF => e
+ # In Ruby 1.9, calling @server_transport.close in shutdown paths causes the select() to raise an
+ # Errno::EBADF. If this happens, ignore it and retry the loop.
+ break
+ end
+ next if rd.nil?
+ socket = @server_transport.accept
+ @logger.debug "Accepted socket: #{socket.inspect}"
+ @io_manager.add_connection socket
+ end
+ rescue IOError => e
+ end
+ # we must be shutting down
+ @logger.info "#{self} is shutting down, goodbye"
+ ensure
+ @transport_semaphore.synchronize do
+ @server_transport.close
+ end
+ @io_manager.ensure_closed unless @io_manager.nil?
+ end
+
+ def shutdown(timeout = 0, block = true)
+ @shutdown_semaphore.synchronize do
+ return if @is_shutdown
+ @is_shutdown = true
+ end
+ # nonblocking is intended for calling from within a Handler
+ # but we can't change the order of operations here, so lets thread
+ shutdown_proc = lambda do
+ @io_manager.shutdown(timeout)
+ @transport_semaphore.synchronize do
+ @server_transport.close # this will break the accept loop
+ end
+ end
+ if block
+ shutdown_proc.call
+ else
+ Thread.new &shutdown_proc
+ end
+ end
+
+ private
+
+ def start_io_manager
+ iom = IOManager.new(@processor, @server_transport, @transport_factory, @protocol_factory, @num_threads, @logger)
+ iom.spawn
+ iom
+ end
+
+ class IOManager # :nodoc:
+ DEFAULT_BUFFER = 2**20
+
+ def initialize(processor, server_transport, transport_factory, protocol_factory, num, logger)
+ @processor = processor
+ @server_transport = server_transport
+ @transport_factory = transport_factory
+ @protocol_factory = protocol_factory
+ @num_threads = num
+ @logger = logger
+ @connections = []
+ @buffers = Hash.new { |h,k| h[k] = '' }
+ @signal_queue = Queue.new
+ @signal_pipes = IO.pipe
+ @signal_pipes[1].sync = true
+ @worker_queue = Queue.new
+ @shutdown_queue = Queue.new
+ end
+
+ def add_connection(socket)
+ signal [:connection, socket]
+ end
+
+ def spawn
+ @iom_thread = Thread.new do
+ @logger.debug "Starting #{self}"
+ run
+ end
+ end
+
+ def shutdown(timeout = 0)
+ @logger.debug "#{self} is shutting down workers"
+ @worker_queue.clear
+ @num_threads.times { @worker_queue.push [:shutdown] }
+ signal [:shutdown, timeout]
+ @shutdown_queue.pop
+ @signal_pipes[0].close
+ @signal_pipes[1].close
+ @logger.debug "#{self} is shutting down, goodbye"
+ end
+
+ def ensure_closed
+ kill_worker_threads if @worker_threads
+ @iom_thread.kill
+ end
+
+ private
+
+ def run
+ spin_worker_threads
+
+ loop do
+ rd, = select([@signal_pipes[0], *@connections])
+ if rd.delete @signal_pipes[0]
+ break if read_signals == :shutdown
+ end
+ rd.each do |fd|
+ begin
+ if fd.handle.eof?
+ remove_connection fd
+ else
+ read_connection fd
+ end
+ rescue Errno::ECONNRESET
+ remove_connection fd
+ end
+ end
+ end
+ join_worker_threads(@shutdown_timeout)
+ ensure
+ @shutdown_queue.push :shutdown
+ end
+
+ def read_connection(fd)
+ @buffers[fd] << fd.read(DEFAULT_BUFFER)
+ while(frame = slice_frame!(@buffers[fd]))
+ @logger.debug "#{self} is processing a frame"
+ @worker_queue.push [:frame, fd, frame]
+ end
+ end
+
+ def spin_worker_threads
+ @logger.debug "#{self} is spinning up worker threads"
+ @worker_threads = []
+ @num_threads.times do
+ @worker_threads << spin_thread
+ end
+ end
+
+ def spin_thread
+ Worker.new(@processor, @transport_factory, @protocol_factory, @logger, @worker_queue).spawn
+ end
+
+ def signal(msg)
+ @signal_queue << msg
+ @signal_pipes[1].write " "
+ end
+
+ def read_signals
+ # clear the signal pipe
+ # note that since read_nonblock is broken in jruby,
+ # we can only read up to a set number of signals at once
+ sigstr = @signal_pipes[0].readpartial(1024)
+ # now read the signals
+ begin
+ sigstr.length.times do
+ signal, obj = @signal_queue.pop(true)
+ case signal
+ when :connection
+ @connections << obj
+ when :shutdown
+ @shutdown_timeout = obj
+ return :shutdown
+ end
+ end
+ rescue ThreadError
+ # out of signals
+ # note that in a perfect world this would never happen, since we're
+ # only reading the number of signals pushed on the pipe, but given the lack
+ # of locks, in theory we could clear the pipe/queue while a new signal is being
+ # placed on the pipe, at which point our next read_signals would hit this error
+ end
+ end
+
+ def remove_connection(fd)
+ # don't explicitly close it, a thread may still be writing to it
+ @connections.delete fd
+ @buffers.delete fd
+ end
+
+ def join_worker_threads(shutdown_timeout)
+ start = Time.now
+ @worker_threads.each do |t|
+ if shutdown_timeout > 0
+ timeout = (start + shutdown_timeout) - Time.now
+ break if timeout <= 0
+ t.join(timeout)
+ else
+ t.join
+ end
+ end
+ kill_worker_threads
+ end
+
+ def kill_worker_threads
+ @worker_threads.each do |t|
+ t.kill if t.status
+ end
+ @worker_threads.clear
+ end
+
+ def slice_frame!(buf)
+ if buf.length >= 4
+ size = buf.unpack('N').first
+ if buf.length >= size + 4
+ buf.slice!(0, size + 4)
+ else
+ nil
+ end
+ else
+ nil
+ end
+ end
+
+ class Worker # :nodoc:
+ def initialize(processor, transport_factory, protocol_factory, logger, queue)
+ @processor = processor
+ @transport_factory = transport_factory
+ @protocol_factory = protocol_factory
+ @logger = logger
+ @queue = queue
+ end
+
+ def spawn
+ Thread.new do
+ @logger.debug "#{self} is spawning"
+ run
+ end
+ end
+
+ private
+
+ def run
+ loop do
+ cmd, *args = @queue.pop
+ case cmd
+ when :shutdown
+ @logger.debug "#{self} is shutting down, goodbye"
+ break
+ when :frame
+ fd, frame = args
+ begin
+ otrans = @transport_factory.get_transport(fd)
+ oprot = @protocol_factory.get_protocol(otrans)
+ membuf = MemoryBufferTransport.new(frame)
+ itrans = @transport_factory.get_transport(membuf)
+ iprot = @protocol_factory.get_protocol(itrans)
+ @processor.process(iprot, oprot)
+ rescue => e
+ @logger.error "#{Thread.current.inspect} raised error: #{e.inspect}\n#{e.backtrace.join("\n")}"
+ end
+ end
+ end
+ end
+ end
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/simple_server.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/simple_server.rb
new file mode 100644
index 0000000000..21e8659266
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/simple_server.rb
@@ -0,0 +1,43 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class SimpleServer < BaseServer
+ def serve
+ begin
+ @server_transport.listen
+ loop do
+ client = @server_transport.accept
+ trans = @transport_factory.get_transport(client)
+ prot = @protocol_factory.get_protocol(trans)
+ begin
+ loop do
+ @processor.process(prot, prot)
+ end
+ rescue Thrift::TransportException, Thrift::ProtocolException
+ ensure
+ trans.close
+ end
+ end
+ ensure
+ @server_transport.close
+ end
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/thin_http_server.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/thin_http_server.rb
new file mode 100644
index 0000000000..4a81c6d177
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/thin_http_server.rb
@@ -0,0 +1,91 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'rack'
+require 'thin'
+
+##
+# Wraps the Thin web server to provide a Thrift server over HTTP.
+module Thrift
+ class ThinHTTPServer < BaseServer
+
+ ##
+ # Accepts a Thrift::Processor
+ # Options include:
+ # * :port
+ # * :ip
+ # * :path
+ # * :protocol_factory
+ def initialize(processor, options={})
+ port = options[:port] || 80
+ ip = options[:ip] || "0.0.0.0"
+ path = options[:path] || "/"
+ protocol_factory = options[:protocol_factory] || BinaryProtocolFactory.new
+ app = RackApplication.for(path, processor, protocol_factory)
+ @server = Thin::Server.new(ip, port, app)
+ end
+
+ ##
+ # Starts the server
+ def serve
+ @server.start
+ end
+
+ class RackApplication
+
+ THRIFT_HEADER = "application/x-thrift"
+
+ def self.for(path, processor, protocol_factory)
+ Rack::Builder.new do
+ use Rack::CommonLogger
+ use Rack::ShowExceptions
+ use Rack::Lint
+ map path do
+ run lambda { |env|
+ request = Rack::Request.new(env)
+ if RackApplication.valid_thrift_request?(request)
+ RackApplication.successful_request(request, processor, protocol_factory)
+ else
+ RackApplication.failed_request
+ end
+ }
+ end
+ end
+ end
+
+ def self.successful_request(rack_request, processor, protocol_factory)
+ response = Rack::Response.new([], 200, {'Content-Type' => THRIFT_HEADER})
+ transport = IOStreamTransport.new rack_request.body, response
+ protocol = protocol_factory.get_protocol transport
+ processor.process protocol, protocol
+ response
+ end
+
+ def self.failed_request
+ Rack::Response.new(['Not Found'], 404, {'Content-Type' => THRIFT_HEADER})
+ end
+
+ def self.valid_thrift_request?(rack_request)
+ rack_request.post? && rack_request.env["CONTENT_TYPE"] == THRIFT_HEADER
+ end
+
+ end
+
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/thread_pool_server.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/thread_pool_server.rb
new file mode 100644
index 0000000000..8cec805a99
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/thread_pool_server.rb
@@ -0,0 +1,75 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'thread'
+
+module Thrift
+ class ThreadPoolServer < BaseServer
+ def initialize(processor, server_transport, transport_factory=nil, protocol_factory=nil, num=20)
+ super(processor, server_transport, transport_factory, protocol_factory)
+ @thread_q = SizedQueue.new(num)
+ @exception_q = Queue.new
+ @running = false
+ end
+
+ ## exceptions that happen in worker threads will be relayed here and
+ ## must be caught. 'retry' can be used to continue. (threads will
+ ## continue to run while the exception is being handled.)
+ def rescuable_serve
+ Thread.new { serve } unless @running
+ @running = true
+ raise @exception_q.pop
+ end
+
+ ## exceptions that happen in worker threads simply cause that thread
+ ## to die and another to be spawned in its place.
+ def serve
+ @server_transport.listen
+
+ begin
+ loop do
+ @thread_q.push(:token)
+ Thread.new do
+ begin
+ loop do
+ client = @server_transport.accept
+ trans = @transport_factory.get_transport(client)
+ prot = @protocol_factory.get_protocol(trans)
+ begin
+ loop do
+ @processor.process(prot, prot)
+ end
+ rescue Thrift::TransportException, Thrift::ProtocolException => e
+ ensure
+ trans.close
+ end
+ end
+ rescue => e
+ @exception_q.push(e)
+ ensure
+ @thread_q.pop # thread died!
+ end
+ end
+ end
+ ensure
+ @server_transport.close
+ end
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/threaded_server.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/threaded_server.rb
new file mode 100644
index 0000000000..a2c917cb86
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/server/threaded_server.rb
@@ -0,0 +1,47 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'thread'
+
+module Thrift
+ class ThreadedServer < BaseServer
+ def serve
+ begin
+ @server_transport.listen
+ loop do
+ client = @server_transport.accept
+ trans = @transport_factory.get_transport(client)
+ prot = @protocol_factory.get_protocol(trans)
+ Thread.new(prot, trans) do |p, t|
+ begin
+ loop do
+ @processor.process(p, p)
+ end
+ rescue Thrift::TransportException, Thrift::ProtocolException
+ ensure
+ t.close
+ end
+ end
+ end
+ ensure
+ @server_transport.close
+ end
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/struct.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/struct.rb
new file mode 100644
index 0000000000..df9d6561c1
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/struct.rb
@@ -0,0 +1,237 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'set'
+
+module Thrift
+ module Struct
+ def initialize(d={}, &block)
+ # get a copy of the default values to work on, removing defaults in favor of arguments
+ fields_with_defaults = fields_with_default_values.dup
+
+ # check if the defaults is empty, or if there are no parameters for this
+ # instantiation, and if so, don't bother overriding defaults.
+ unless fields_with_defaults.empty? || d.empty?
+ d.each_key do |name|
+ fields_with_defaults.delete(name.to_s)
+ end
+ end
+
+ # assign all the user-specified arguments
+ unless d.empty?
+ d.each do |name, value|
+ unless name_to_id(name.to_s)
+ raise Exception, "Unknown key given to #{self.class}.new: #{name}"
+ end
+ Thrift.check_type(value, struct_fields[name_to_id(name.to_s)], name) if Thrift.type_checking
+ instance_variable_set("@#{name}", value)
+ end
+ end
+
+ # assign all the default values
+ unless fields_with_defaults.empty?
+ fields_with_defaults.each do |name, default_value|
+ instance_variable_set("@#{name}", (default_value.dup rescue default_value))
+ end
+ end
+
+ yield self if block_given?
+ end
+
+ def fields_with_default_values
+ fields_with_default_values = self.class.instance_variable_get(:@fields_with_default_values)
+ unless fields_with_default_values
+ fields_with_default_values = {}
+ struct_fields.each do |fid, field_def|
+ unless field_def[:default].nil?
+ fields_with_default_values[field_def[:name]] = field_def[:default]
+ end
+ end
+ self.class.instance_variable_set(:@fields_with_default_values, fields_with_default_values)
+ end
+ fields_with_default_values
+ end
+
+ def inspect(skip_optional_nulls = true)
+ fields = []
+ each_field do |fid, field_info|
+ name = field_info[:name]
+ value = instance_variable_get("@#{name}")
+ unless skip_optional_nulls && field_info[:optional] && value.nil?
+ fields << "#{name}:#{inspect_field(value, field_info)}"
+ end
+ end
+ "<#{self.class} #{fields.join(", ")}>"
+ end
+
+ def read(iprot)
+ iprot.read_struct_begin
+ loop do
+ fname, ftype, fid = iprot.read_field_begin
+ break if (ftype == Types::STOP)
+ handle_message(iprot, fid, ftype)
+ iprot.read_field_end
+ end
+ iprot.read_struct_end
+ validate
+ end
+
+ def write(oprot)
+ validate
+ oprot.write_struct_begin(self.class.name)
+ each_field do |fid, field_info|
+ name = field_info[:name]
+ type = field_info[:type]
+ value = instance_variable_get("@#{name}")
+ unless value.nil?
+ if is_container? type
+ oprot.write_field_begin(name, type, fid)
+ write_container(oprot, value, field_info)
+ oprot.write_field_end
+ else
+ oprot.write_field(field_info, fid, value)
+ end
+ end
+ end
+ oprot.write_field_stop
+ oprot.write_struct_end
+ end
+
+ def ==(other)
+ return false if other.nil?
+ each_field do |fid, field_info|
+ name = field_info[:name]
+ return false unless other.respond_to?(name) && self.send(name) == other.send(name)
+ end
+ true
+ end
+
+ def eql?(other)
+ self.class == other.class && self == other
+ end
+
+ # This implementation of hash() is inspired by Apache's Java HashCodeBuilder class.
+ def hash
+ total = 17
+ each_field do |fid, field_info|
+ name = field_info[:name]
+ value = self.send(name)
+ total = (total * 37 + value.hash) & 0xffffffff
+ end
+ total
+ end
+
+ def differences(other)
+ diffs = []
+ unless other.is_a?(self.class)
+ diffs << "Different class!"
+ else
+ each_field do |fid, field_info|
+ name = field_info[:name]
+ diffs << "#{name} differs!" unless self.instance_variable_get("@#{name}") == other.instance_variable_get("@#{name}")
+ end
+ end
+ diffs
+ end
+
+ def self.field_accessor(klass, field_info)
+ field_name_sym = field_info[:name].to_sym
+ klass.send :attr_reader, field_name_sym
+ klass.send :define_method, "#{field_info[:name]}=" do |value|
+ Thrift.check_type(value, field_info, field_info[:name]) if Thrift.type_checking
+ instance_variable_set("@#{field_name_sym}", value)
+ end
+ end
+
+ def self.generate_accessors(klass)
+ klass::FIELDS.values.each do |field_info|
+ field_accessor(klass, field_info)
+ qmark_isset_method(klass, field_info)
+ end
+ end
+
+ def self.qmark_isset_method(klass, field_info)
+ klass.send :define_method, "#{field_info[:name]}?" do
+ !self.send(field_info[:name].to_sym).nil?
+ end
+ end
+
+ def <=>(other)
+ if self.class == other.class
+ each_field do |fid, field_info|
+ v1 = self.send(field_info[:name])
+ v1_set = !v1.nil?
+ v2 = other.send(field_info[:name])
+ v2_set = !v2.nil?
+ if v1_set && !v2_set
+ return -1
+ elsif !v1_set && v2_set
+ return 1
+ elsif v1_set && v2_set
+ cmp = v1 <=> v2
+ if cmp != 0
+ return cmp
+ end
+ end
+ end
+ 0
+ else
+ self.class <=> other.class
+ end
+ end
+
+ protected
+
+ def self.append_features(mod)
+ if mod.ancestors.include? ::Exception
+ mod.send :class_variable_set, :'@@__thrift_struct_real_initialize', mod.instance_method(:initialize)
+ super
+ # set up our custom initializer so `raise Xception, 'message'` works
+ mod.send :define_method, :struct_initialize, mod.instance_method(:initialize)
+ mod.send :define_method, :initialize, mod.instance_method(:exception_initialize)
+ else
+ super
+ end
+ end
+
+ def exception_initialize(*args, &block)
+ if args.size == 1 and args.first.is_a? Hash
+ # looks like it's a regular Struct initialize
+ method(:struct_initialize).call(args.first)
+ else
+ # call the Struct initializer first with no args
+ # this will set our field default values
+ method(:struct_initialize).call()
+ # now give it to the exception
+ self.class.send(:class_variable_get, :'@@__thrift_struct_real_initialize').bind(self).call(*args, &block) if args.size > 0
+ # self.class.instance_method(:initialize).bind(self).call(*args, &block)
+ end
+ end
+
+ def handle_message(iprot, fid, ftype)
+ field = struct_fields[fid]
+ if field and field[:type] == ftype
+ value = read_field(iprot, field)
+ instance_variable_set("@#{field[:name]}", value)
+ else
+ iprot.skip(ftype)
+ end
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/struct_union.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/struct_union.rb
new file mode 100644
index 0000000000..e21b39ebf9
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/struct_union.rb
@@ -0,0 +1,192 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+require 'set'
+
+module Thrift
+ module Struct_Union
+ def name_to_id(name)
+ names_to_ids = self.class.instance_variable_get(:@names_to_ids)
+ unless names_to_ids
+ names_to_ids = {}
+ struct_fields.each do |fid, field_def|
+ names_to_ids[field_def[:name]] = fid
+ end
+ self.class.instance_variable_set(:@names_to_ids, names_to_ids)
+ end
+ names_to_ids[name]
+ end
+
+ def sorted_field_ids
+ sorted_field_ids = self.class.instance_variable_get(:@sorted_field_ids)
+ unless sorted_field_ids
+ sorted_field_ids = struct_fields.keys.sort
+ self.class.instance_variable_set(:@sorted_field_ids, sorted_field_ids)
+ end
+ sorted_field_ids
+ end
+
+ def each_field
+ sorted_field_ids.each do |fid|
+ data = struct_fields[fid]
+ yield fid, data
+ end
+ end
+
+ def read_field(iprot, field = {})
+ case field[:type]
+ when Types::STRUCT
+ value = field[:class].new
+ value.read(iprot)
+ when Types::MAP
+ key_type, val_type, size = iprot.read_map_begin
+ # Skip the map contents if the declared key or value types don't match the expected ones.
+ if (size != 0 && (key_type != field[:key][:type] || val_type != field[:value][:type]))
+ size.times do
+ iprot.skip(key_type)
+ iprot.skip(val_type)
+ end
+ value = nil
+ else
+ value = {}
+ size.times do
+ k = read_field(iprot, field_info(field[:key]))
+ v = read_field(iprot, field_info(field[:value]))
+ value[k] = v
+ end
+ end
+ iprot.read_map_end
+ when Types::LIST
+ e_type, size = iprot.read_list_begin
+ # Skip the list contents if the declared element type doesn't match the expected one.
+ if (e_type != field[:element][:type])
+ size.times do
+ iprot.skip(e_type)
+ end
+ value = nil
+ else
+ value = Array.new(size) do |n|
+ read_field(iprot, field_info(field[:element]))
+ end
+ end
+ iprot.read_list_end
+ when Types::SET
+ e_type, size = iprot.read_set_begin
+ # Skip the set contents if the declared element type doesn't match the expected one.
+ if (e_type != field[:element][:type])
+ size.times do
+ iprot.skip(e_type)
+ end
+ else
+ value = Set.new
+ size.times do
+ element = read_field(iprot, field_info(field[:element]))
+ value << element
+ end
+ end
+ iprot.read_set_end
+ else
+ value = iprot.read_type(field)
+ end
+ value
+ end
+
+ def write_data(oprot, value, field)
+ if is_container? field[:type]
+ write_container(oprot, value, field)
+ else
+ oprot.write_type(field, value)
+ end
+ end
+
+ def write_container(oprot, value, field = {})
+ case field[:type]
+ when Types::MAP
+ oprot.write_map_begin(field[:key][:type], field[:value][:type], value.size)
+ value.each do |k, v|
+ write_data(oprot, k, field[:key])
+ write_data(oprot, v, field[:value])
+ end
+ oprot.write_map_end
+ when Types::LIST
+ oprot.write_list_begin(field[:element][:type], value.size)
+ value.each do |elem|
+ write_data(oprot, elem, field[:element])
+ end
+ oprot.write_list_end
+ when Types::SET
+ oprot.write_set_begin(field[:element][:type], value.size)
+ value.each do |v,| # the , is to preserve compatibility with the old Hash-style sets
+ write_data(oprot, v, field[:element])
+ end
+ oprot.write_set_end
+ else
+ raise "Not a container type: #{field[:type]}"
+ end
+ end
+
+ CONTAINER_TYPES = []
+ CONTAINER_TYPES[Types::LIST] = true
+ CONTAINER_TYPES[Types::MAP] = true
+ CONTAINER_TYPES[Types::SET] = true
+ def is_container?(type)
+ CONTAINER_TYPES[type]
+ end
+
+ def field_info(field)
+ { :type => field[:type],
+ :class => field[:class],
+ :key => field[:key],
+ :value => field[:value],
+ :element => field[:element] }
+ end
+
+ def inspect_field(value, field_info)
+ if enum_class = field_info[:enum_class]
+ "#{enum_class.const_get(:VALUE_MAP)[value]} (#{value})"
+ elsif value.is_a? Hash
+ if field_info[:type] == Types::MAP
+ map_buf = []
+ value.each do |k, v|
+ map_buf << inspect_field(k, field_info[:key]) + ": " + inspect_field(v, field_info[:value])
+ end
+ "{" + map_buf.join(", ") + "}"
+ else
+ # old-style set
+ inspect_collection(value.keys, field_info)
+ end
+ elsif value.is_a? Array
+ inspect_collection(value, field_info)
+ elsif value.is_a? Set
+ inspect_collection(value, field_info)
+ elsif value.is_a?(String) && field_info[:binary]
+ value.unpack("H*").first
+ else
+ value.inspect
+ end
+ end
+
+ def inspect_collection(collection, field_info)
+ buf = []
+ collection.each do |k|
+ buf << inspect_field(k, field_info[:element])
+ end
+ "[" + buf.join(", ") + "]"
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/thrift_native.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/thrift_native.rb
new file mode 100644
index 0000000000..4d8df61ff4
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/thrift_native.rb
@@ -0,0 +1,24 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+begin
+ require "thrift_native"
+rescue LoadError
+ puts "Unable to load thrift_native extension. Defaulting to pure Ruby libraries."
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/base_server_transport.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/base_server_transport.rb
new file mode 100644
index 0000000000..68c5af076f
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/base_server_transport.rb
@@ -0,0 +1,37 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class BaseServerTransport
+ def listen
+ raise NotImplementedError
+ end
+
+ def accept
+ raise NotImplementedError
+ end
+
+ def close; nil; end
+
+ def closed?
+ raise NotImplementedError
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/base_transport.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/base_transport.rb
new file mode 100644
index 0000000000..879032644f
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/base_transport.rb
@@ -0,0 +1,109 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class TransportException < Exception
+ UNKNOWN = 0
+ NOT_OPEN = 1
+ ALREADY_OPEN = 2
+ TIMED_OUT = 3
+ END_OF_FILE = 4
+
+ attr_reader :type
+
+ def initialize(type=UNKNOWN, message=nil)
+ super(message)
+ @type = type
+ end
+ end
+
+ module TransportUtils
+ # Deprecated: Use Thrift::Bytes instead
+ def self.get_string_byte(string, index)
+ Bytes.get_string_byte(string, index)
+ end
+
+ # Deprecated: Use Thrift::Bytes instead
+ def self.set_string_byte(string, index, byte)
+ Bytes.set_string_byte(string, index, byte)
+ end
+ end
+
+ class BaseTransport
+ def open?; end
+
+ def open; end
+
+ def close; end
+
+ # Reads a number of bytes from the transports. In Ruby 1.9+, the String returned will have a BINARY (aka ASCII8BIT) encoding.
+ #
+ # sz - The number of bytes to read from the transport.
+ #
+ # Returns a String acting as a byte buffer.
+ def read(sz)
+ raise NotImplementedError
+ end
+
+ # Returns an unsigned byte as a Fixnum in the range (0..255).
+ def read_byte
+ buf = read_all(1)
+ return Bytes.get_string_byte(buf, 0)
+ end
+
+ # Reads size bytes and copies them into buffer[0..size].
+ def read_into_buffer(buffer, size)
+ tmp = read_all(size)
+ i = 0
+ tmp.each_byte do |byte|
+ Bytes.set_string_byte(buffer, i, byte)
+ i += 1
+ end
+ i
+ end
+
+ def read_all(size)
+ return Bytes.empty_byte_buffer if size <= 0
+ buf = read(size)
+ while (buf.length < size)
+ chunk = read(size - buf.length)
+ buf << chunk
+ end
+
+ buf
+ end
+
+ # Writes the byte buffer to the transport. In Ruby 1.9+, the buffer will be forced into BINARY encoding.
+ #
+ # buf - A String acting as a byte buffer.
+ #
+ # Returns nothing.
+ def write(buf); end
+ alias_method :<<, :write
+
+ def flush; end
+ end
+
+ class BaseTransportFactory
+ def get_transport(trans)
+ return trans
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/buffered_transport.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/buffered_transport.rb
new file mode 100644
index 0000000000..781d3c69cf
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/buffered_transport.rb
@@ -0,0 +1,114 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class BufferedTransport < BaseTransport
+ DEFAULT_BUFFER = 4096
+
+ def initialize(transport)
+ @transport = transport
+ @wbuf = Bytes.empty_byte_buffer
+ @rbuf = Bytes.empty_byte_buffer
+ @index = 0
+ end
+
+ def open?
+ return @transport.open?
+ end
+
+ def open
+ @transport.open
+ end
+
+ def close
+ flush
+ @transport.close
+ end
+
+ def read(sz)
+ @index += sz
+ ret = @rbuf.slice(@index - sz, sz) || Bytes.empty_byte_buffer
+
+ if ret.length == 0
+ @rbuf = @transport.read([sz, DEFAULT_BUFFER].max)
+ @index = sz
+ ret = @rbuf.slice(0, sz) || Bytes.empty_byte_buffer
+ end
+
+ ret
+ end
+
+ def read_byte
+ # If the read buffer is exhausted, try to read up to DEFAULT_BUFFER more bytes into it.
+ if @index >= @rbuf.size
+ @rbuf = @transport.read(DEFAULT_BUFFER)
+ @index = 0
+ end
+
+ # The read buffer has some data now, read a single byte. Using get_string_byte() avoids
+ # allocating a temp string of size 1 unnecessarily.
+ @index += 1
+ return Bytes.get_string_byte(@rbuf, @index - 1)
+ end
+
+ # Reads a number of bytes from the transport into the buffer passed.
+ #
+ # buffer - The String (byte buffer) to write data to; this is assumed to have a BINARY encoding.
+ # size - The number of bytes to read from the transport and write to the buffer.
+ #
+ # Returns the number of bytes read.
+ def read_into_buffer(buffer, size)
+ i = 0
+ while i < size
+ # If the read buffer is exhausted, try to read up to DEFAULT_BUFFER more bytes into it.
+ if @index >= @rbuf.size
+ @rbuf = @transport.read(DEFAULT_BUFFER)
+ @index = 0
+ end
+
+ # The read buffer has some data now, so copy bytes over to the output buffer.
+ byte = Bytes.get_string_byte(@rbuf, @index)
+ Bytes.set_string_byte(buffer, i, byte)
+ @index += 1
+ i += 1
+ end
+ i
+ end
+
+ def write(buf)
+ @wbuf << Bytes.force_binary_encoding(buf)
+ end
+
+ def flush
+ unless @wbuf.empty?
+ @transport.write(@wbuf)
+ @wbuf = Bytes.empty_byte_buffer
+ end
+
+ @transport.flush
+ end
+ end
+
+ class BufferedTransportFactory < BaseTransportFactory
+ def get_transport(transport)
+ return BufferedTransport.new(transport)
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/framed_transport.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/framed_transport.rb
new file mode 100644
index 0000000000..d806ce022b
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/framed_transport.rb
@@ -0,0 +1,117 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class FramedTransport < BaseTransport
+ def initialize(transport, read=true, write=true)
+ @transport = transport
+ @rbuf = Bytes.empty_byte_buffer
+ @wbuf = Bytes.empty_byte_buffer
+ @read = read
+ @write = write
+ @index = 0
+ end
+
+ def open?
+ @transport.open?
+ end
+
+ def open
+ @transport.open
+ end
+
+ def close
+ @transport.close
+ end
+
+ def read(sz)
+ return @transport.read(sz) unless @read
+
+ return Bytes.empty_byte_buffer if sz <= 0
+
+ read_frame if @index >= @rbuf.length
+
+ @index += sz
+ @rbuf.slice(@index - sz, sz) || Bytes.empty_byte_buffer
+ end
+
+ def read_byte
+ return @transport.read_byte() unless @read
+
+ read_frame if @index >= @rbuf.length
+
+ # The read buffer has some data now, read a single byte. Using get_string_byte() avoids
+ # allocating a temp string of size 1 unnecessarily.
+ @index += 1
+ return Bytes.get_string_byte(@rbuf, @index - 1)
+ end
+
+ def read_into_buffer(buffer, size)
+ i = 0
+ while i < size
+ read_frame if @index >= @rbuf.length
+
+ # The read buffer has some data now, so copy bytes over to the output buffer.
+ byte = Bytes.get_string_byte(@rbuf, @index)
+ Bytes.set_string_byte(buffer, i, byte)
+ @index += 1
+ i += 1
+ end
+ i
+ end
+
+ def write(buf, sz=nil)
+ return @transport.write(buf) unless @write
+
+ buf = Bytes.force_binary_encoding(buf)
+ @wbuf << (sz ? buf[0...sz] : buf)
+ end
+
+ #
+ # Writes the output buffer to the stream in the format of a 4-byte length
+ # followed by the actual data.
+ #
+ def flush
+ return @transport.flush unless @write
+
+ out = [@wbuf.length].pack('N')
+ # Array#pack should return a BINARY encoded String, so it shouldn't be necessary to force encoding
+ out << @wbuf
+ @transport.write(out)
+ @transport.flush
+ @wbuf = Bytes.empty_byte_buffer
+ end
+
+ private
+
+ def read_frame
+ sz = @transport.read_all(4).unpack('N').first
+
+ @index = 0
+ @rbuf = @transport.read_all(sz)
+ end
+ end
+
+ class FramedTransportFactory < BaseTransportFactory
+ def get_transport(transport)
+ return FramedTransport.new(transport)
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/http_client_transport.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/http_client_transport.rb
new file mode 100644
index 0000000000..c9c4fec8d8
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/http_client_transport.rb
@@ -0,0 +1,57 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'net/http'
+require 'net/https'
+require 'openssl'
+require 'uri'
+require 'stringio'
+
+module Thrift
+ class HTTPClientTransport < BaseTransport
+
+ def initialize(url, opts = {})
+ @url = URI url
+ @headers = {'Content-Type' => 'application/x-thrift'}
+ @outbuf = Bytes.empty_byte_buffer
+ @ssl_verify_mode = opts.fetch(:ssl_verify_mode, OpenSSL::SSL::VERIFY_PEER)
+ end
+
+ def open?; true end
+ def read(sz); @inbuf.read sz end
+ def write(buf); @outbuf << Bytes.force_binary_encoding(buf) end
+
+ def add_headers(headers)
+ @headers = @headers.merge(headers)
+ end
+
+ def flush
+ http = Net::HTTP.new @url.host, @url.port
+ http.use_ssl = @url.scheme == 'https'
+ http.verify_mode = @ssl_verify_mode if @url.scheme == 'https'
+ resp = http.post(@url.request_uri, @outbuf, @headers)
+ data = resp.body
+ data = Bytes.force_binary_encoding(data)
+ @inbuf = StringIO.new data
+ ensure
+ @outbuf = Bytes.empty_byte_buffer
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/io_stream_transport.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/io_stream_transport.rb
new file mode 100644
index 0000000000..e3c8379da6
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/io_stream_transport.rb
@@ -0,0 +1,39 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+# Very very simple implementation of wrapping two objects, one with a #read
+# method and one with a #write method, into a transport for thrift.
+#
+# Assumes both objects are open, remain open, don't require flushing, etc.
+#
+module Thrift
+ class IOStreamTransport < BaseTransport
+ def initialize(input, output)
+ @input = input
+ @output = output
+ end
+
+ def open?; not @input.closed? or not @output.closed? end
+ def read(sz); @input.read(sz) end
+ def write(buf); @output.write(Bytes.force_binary_encoding(buf)) end
+ def close; @input.close; @output.close end
+ def to_io; @input end # we're assuming this is used in a IO.select for reading
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/memory_buffer_transport.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/memory_buffer_transport.rb
new file mode 100644
index 0000000000..ad5ad85558
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/memory_buffer_transport.rb
@@ -0,0 +1,125 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class MemoryBufferTransport < BaseTransport
+ GARBAGE_BUFFER_SIZE = 4*(2**10) # 4kB
+
+ # If you pass a string to this, you should #dup that string
+ # unless you want it to be modified by #read and #write
+ #--
+ # this behavior is no longer required. If you wish to change it
+ # go ahead, just make sure the specs pass
+ def initialize(buffer = nil)
+ @buf = buffer ? Bytes.force_binary_encoding(buffer) : Bytes.empty_byte_buffer
+ @index = 0
+ end
+
+ def open?
+ return true
+ end
+
+ def open
+ end
+
+ def close
+ end
+
+ def peek
+ @index < @buf.size
+ end
+
+ # this method does not use the passed object directly but copies it
+ def reset_buffer(new_buf = '')
+ @buf.replace Bytes.force_binary_encoding(new_buf)
+ @index = 0
+ end
+
+ def available
+ @buf.length - @index
+ end
+
+ def read(len)
+ data = @buf.slice(@index, len)
+ @index += len
+ @index = @buf.size if @index > @buf.size
+ if @index >= GARBAGE_BUFFER_SIZE
+ @buf = @buf.slice(@index..-1)
+ @index = 0
+ end
+ if data.size < len
+ raise EOFError, "Not enough bytes remain in buffer"
+ end
+ data
+ end
+
+ def read_byte
+ raise EOFError.new("Not enough bytes remain in buffer") if @index >= @buf.size
+ val = Bytes.get_string_byte(@buf, @index)
+ @index += 1
+ if @index >= GARBAGE_BUFFER_SIZE
+ @buf = @buf.slice(@index..-1)
+ @index = 0
+ end
+ val
+ end
+
+ def read_into_buffer(buffer, size)
+ i = 0
+ while i < size
+ raise EOFError.new("Not enough bytes remain in buffer") if @index >= @buf.size
+
+ # The read buffer has some data now, so copy bytes over to the output buffer.
+ byte = Bytes.get_string_byte(@buf, @index)
+ Bytes.set_string_byte(buffer, i, byte)
+ @index += 1
+ i += 1
+ end
+ if @index >= GARBAGE_BUFFER_SIZE
+ @buf = @buf.slice(@index..-1)
+ @index = 0
+ end
+ i
+ end
+
+ def write(wbuf)
+ @buf << Bytes.force_binary_encoding(wbuf)
+ end
+
+ def flush
+ end
+
+ def inspect_buffer
+ out = []
+ for idx in 0...(@buf.size)
+ # if idx != 0
+ # out << " "
+ # end
+
+ if idx == @index
+ out << ">"
+ end
+
+ out << @buf[idx].ord.to_s(16)
+ end
+ out.join(" ")
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/server_socket.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/server_socket.rb
new file mode 100644
index 0000000000..7feb9ab0d1
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/server_socket.rb
@@ -0,0 +1,63 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'socket'
+
+module Thrift
+ class ServerSocket < BaseServerTransport
+ # call-seq: initialize(host = nil, port)
+ def initialize(host_or_port, port = nil)
+ if port
+ @host = host_or_port
+ @port = port
+ else
+ @host = nil
+ @port = host_or_port
+ end
+ @handle = nil
+ end
+
+ attr_reader :handle
+
+ def listen
+ @handle = TCPServer.new(@host, @port)
+ end
+
+ def accept
+ unless @handle.nil?
+ sock = @handle.accept
+ trans = Socket.new
+ trans.handle = sock
+ trans
+ end
+ end
+
+ def close
+ @handle.close unless @handle.nil? or @handle.closed?
+ @handle = nil
+ end
+
+ def closed?
+ @handle.nil? or @handle.closed?
+ end
+
+ alias to_io handle
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/socket.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/socket.rb
new file mode 100644
index 0000000000..517d112aac
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/socket.rb
@@ -0,0 +1,141 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'socket'
+
+module Thrift
+ class Socket < BaseTransport
+ def initialize(host='localhost', port=9090, timeout=nil)
+ @host = host
+ @port = port
+ @timeout = timeout
+ @desc = "#{host}:#{port}"
+ @handle = nil
+ end
+
+ attr_accessor :handle, :timeout
+
+ def open
+ for addrinfo in ::Socket::getaddrinfo(@host, @port, nil, ::Socket::SOCK_STREAM) do
+ begin
+ socket = ::Socket.new(addrinfo[4], ::Socket::SOCK_STREAM, 0)
+ socket.setsockopt(::Socket::IPPROTO_TCP, ::Socket::TCP_NODELAY, 1)
+ sockaddr = ::Socket.sockaddr_in(addrinfo[1], addrinfo[3])
+ begin
+ socket.connect_nonblock(sockaddr)
+ rescue Errno::EINPROGRESS
+ unless IO.select(nil, [ socket ], nil, @timeout)
+ next
+ end
+ begin
+ socket.connect_nonblock(sockaddr)
+ rescue Errno::EISCONN
+ end
+ end
+ return @handle = socket
+ rescue StandardError => e
+ next
+ end
+ end
+ raise TransportException.new(TransportException::NOT_OPEN, "Could not connect to #{@desc}: #{e}")
+ end
+
+ def open?
+ !@handle.nil? and !@handle.closed?
+ end
+
+ def write(str)
+ raise IOError, "closed stream" unless open?
+ str = Bytes.force_binary_encoding(str)
+ begin
+ if @timeout.nil? or @timeout == 0
+ @handle.write(str)
+ else
+ len = 0
+ start = Time.now
+ while Time.now - start < @timeout
+ rd, wr, = IO.select(nil, [@handle], nil, @timeout)
+ if wr and not wr.empty?
+ len += @handle.write_nonblock(str[len..-1])
+ break if len >= str.length
+ end
+ end
+ if len < str.length
+ raise TransportException.new(TransportException::TIMED_OUT, "Socket: Timed out writing #{str.length} bytes to #{@desc}")
+ else
+ len
+ end
+ end
+ rescue TransportException => e
+ # pass this on
+ raise e
+ rescue StandardError => e
+ @handle.close
+ @handle = nil
+ raise TransportException.new(TransportException::NOT_OPEN, e.message)
+ end
+ end
+
+ def read(sz)
+ raise IOError, "closed stream" unless open?
+
+ begin
+ if @timeout.nil? or @timeout == 0
+ data = @handle.readpartial(sz)
+ else
+ # it's possible to interrupt select for something other than the timeout
+ # so we need to ensure we've waited long enough, but not too long
+ start = Time.now
+ timespent = 0
+ rd = loop do
+ rd, = IO.select([@handle], nil, nil, @timeout - timespent)
+ timespent = Time.now - start
+ break rd if (rd and not rd.empty?) or timespent >= @timeout
+ end
+ if rd.nil? or rd.empty?
+ raise TransportException.new(TransportException::TIMED_OUT, "Socket: Timed out reading #{sz} bytes from #{@desc}")
+ else
+ data = @handle.readpartial(sz)
+ end
+ end
+ rescue TransportException => e
+ # don't let this get caught by the StandardError handler
+ raise e
+ rescue StandardError => e
+ @handle.close unless @handle.closed?
+ @handle = nil
+ raise TransportException.new(TransportException::NOT_OPEN, e.message)
+ end
+ if (data.nil? or data.length == 0)
+ raise TransportException.new(TransportException::UNKNOWN, "Socket: Could not read #{sz} bytes from #{@desc}")
+ end
+ data
+ end
+
+ def close
+ @handle.close unless @handle.nil? or @handle.closed?
+ @handle = nil
+ end
+
+ def to_io
+ @handle
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/ssl_server_socket.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/ssl_server_socket.rb
new file mode 100644
index 0000000000..abc1343902
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/ssl_server_socket.rb
@@ -0,0 +1,37 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'socket'
+
+module Thrift
+ class SSLServerSocket < ServerSocket
+ def initialize(host_or_port, port = nil, ssl_context = nil)
+ super(host_or_port, port)
+ @ssl_context = ssl_context
+ end
+
+ attr_accessor :ssl_context
+
+ def listen
+ socket = TCPServer.new(@host, @port)
+ @handle = OpenSSL::SSL::SSLServer.new(socket, @ssl_context)
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/ssl_socket.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/ssl_socket.rb
new file mode 100644
index 0000000000..dbbcc94fac
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/ssl_socket.rb
@@ -0,0 +1,47 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+
+module Thrift
+ class SSLSocket < Socket
+ def initialize(host='localhost', port=9090, timeout=nil, ssl_context=nil)
+ super(host, port, timeout)
+ @ssl_context = ssl_context
+ end
+
+ attr_accessor :ssl_context
+
+ def open
+ socket = super
+ @handle = OpenSSL::SSL::SSLSocket.new(socket, @ssl_context)
+ begin
+ @handle.connect_nonblock
+ @handle.post_connection_check(@host)
+ @handle
+ rescue IO::WaitReadable
+ IO.select([ @handle ], nil, nil, @timeout)
+ retry
+ rescue IO::WaitWritable
+ IO.select(nil, [ @handle ], nil, @timeout)
+ retry
+ rescue StandardError => e
+ raise TransportException.new(TransportException::NOT_OPEN, "Could not connect to #{@desc}: #{e}")
+ end
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/unix_server_socket.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/unix_server_socket.rb
new file mode 100644
index 0000000000..a135d25f24
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/unix_server_socket.rb
@@ -0,0 +1,60 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'socket'
+
+module Thrift
+ class UNIXServerSocket < BaseServerTransport
+ def initialize(path)
+ @path = path
+ @handle = nil
+ end
+
+ attr_accessor :handle
+
+ def listen
+ @handle = ::UNIXServer.new(@path)
+ end
+
+ def accept
+ unless @handle.nil?
+ sock = @handle.accept
+ trans = UNIXSocket.new(nil)
+ trans.handle = sock
+ trans
+ end
+ end
+
+ def close
+ if @handle
+ @handle.close unless @handle.closed?
+ @handle = nil
+ # UNIXServer doesn't delete the socket file, so we have to do it ourselves
+ File.delete(@path)
+ end
+ end
+
+ def closed?
+ @handle.nil? or @handle.closed?
+ end
+
+ alias to_io handle
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/unix_socket.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/unix_socket.rb
new file mode 100644
index 0000000000..8f692e4c86
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/transport/unix_socket.rb
@@ -0,0 +1,40 @@
+# encoding: ascii-8bit
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'socket'
+
+module Thrift
+ class UNIXSocket < Socket
+ def initialize(path, timeout=nil)
+ @path = path
+ @timeout = timeout
+ @desc = @path # for read()'s error
+ @handle = nil
+ end
+
+ def open
+ begin
+ @handle = ::UNIXSocket.new(@path)
+ rescue StandardError
+ raise TransportException.new(TransportException::NOT_OPEN, "Could not open UNIX socket at #{@path}")
+ end
+ end
+ end
+end
\ No newline at end of file
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/types.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/types.rb
new file mode 100644
index 0000000000..cac52691a7
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/types.rb
@@ -0,0 +1,101 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+require 'set'
+
+module Thrift
+ module Types
+ STOP = 0
+ VOID = 1
+ BOOL = 2
+ BYTE = 3
+ DOUBLE = 4
+ I16 = 6
+ I32 = 8
+ I64 = 10
+ STRING = 11
+ STRUCT = 12
+ MAP = 13
+ SET = 14
+ LIST = 15
+ end
+
+ class << self
+ attr_accessor :type_checking
+ end
+
+ class TypeError < Exception
+ end
+
+ def self.check_type(value, field, name, skip_nil=true)
+ return if value.nil? and skip_nil
+ klasses = case field[:type]
+ when Types::VOID
+ NilClass
+ when Types::BOOL
+ [TrueClass, FalseClass]
+ when Types::BYTE, Types::I16, Types::I32, Types::I64
+ Integer
+ when Types::DOUBLE
+ Float
+ when Types::STRING
+ String
+ when Types::STRUCT
+ [Struct, Union]
+ when Types::MAP
+ Hash
+ when Types::SET
+ Set
+ when Types::LIST
+ Array
+ end
+ valid = klasses && [*klasses].any? { |klass| klass === value }
+ raise TypeError, "Expected #{type_name(field[:type])}, received #{value.class} for field #{name}" unless valid
+ # check elements now
+ case field[:type]
+ when Types::MAP
+ value.each_pair do |k,v|
+ check_type(k, field[:key], "#{name}.key", false)
+ check_type(v, field[:value], "#{name}.value", false)
+ end
+ when Types::SET, Types::LIST
+ value.each do |el|
+ check_type(el, field[:element], "#{name}.element", false)
+ end
+ when Types::STRUCT
+ raise TypeError, "Expected #{field[:class]}, received #{value.class} for field #{name}" unless field[:class] == value.class
+ end
+ end
+
+ def self.type_name(type)
+ Types.constants.each do |const|
+ return "Types::#{const}" if Types.const_get(const) == type
+ end
+ nil
+ end
+
+ module MessageTypes
+ CALL = 1
+ REPLY = 2
+ EXCEPTION = 3
+ ONEWAY = 4
+ end
+end
+
+Thrift.type_checking = false if Thrift.type_checking.nil?
diff --git a/debian/gems-compat/thrift-0.11.0.0/lib/thrift/union.rb b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/union.rb
new file mode 100644
index 0000000000..490c55c406
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/lib/thrift/union.rb
@@ -0,0 +1,176 @@
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+module Thrift
+ class Union
+ def initialize(name=nil, value=nil)
+ if name
+ if name.is_a? Hash
+ if name.size > 1
+ raise "#{self.class} cannot be instantiated with more than one field!"
+ end
+
+ name, value = name.keys.first, name.values.first
+ end
+
+ if Thrift.type_checking
+ raise Exception, "#{self.class} does not contain a field named #{name}!" unless name_to_id(name.to_s)
+ end
+
+ if value.nil?
+ raise Exception, "Union #{self.class} cannot be instantiated with setfield and nil value!"
+ end
+
+ Thrift.check_type(value, struct_fields[name_to_id(name.to_s)], name) if Thrift.type_checking
+ elsif !value.nil?
+ raise Exception, "Value provided, but no name!"
+ end
+ @setfield = name
+ @value = value
+ end
+
+ def inspect
+ if get_set_field
+ "<#{self.class} #{@setfield}: #{inspect_field(@value, struct_fields[name_to_id(@setfield.to_s)])}>"
+ else
+ "<#{self.class} >"
+ end
+ end
+
+ def read(iprot)
+ iprot.read_struct_begin
+ fname, ftype, fid = iprot.read_field_begin
+ handle_message(iprot, fid, ftype)
+ iprot.read_field_end
+
+ fname, ftype, fid = iprot.read_field_begin
+ raise "Too many fields for union" unless (ftype == Types::STOP)
+
+ iprot.read_struct_end
+ validate
+ end
+
+ def write(oprot)
+ validate
+ oprot.write_struct_begin(self.class.name)
+
+ fid = self.name_to_id(@setfield.to_s)
+
+ field_info = struct_fields[fid]
+ type = field_info[:type]
+ if is_container? type
+ oprot.write_field_begin(@setfield, type, fid)
+ write_container(oprot, @value, field_info)
+ oprot.write_field_end
+ else
+ oprot.write_field(@setfield, type, fid, @value)
+ end
+
+ oprot.write_field_stop
+ oprot.write_struct_end
+ end
+
+ def ==(other)
+ other.equal?(self) || other.instance_of?(self.class) && @setfield == other.get_set_field && @value == other.get_value
+ end
+ alias_method :eql?, :==
+
+ def hash
+ [self.class.name, @setfield, @value].hash
+ end
+
+ def self.field_accessor(klass, field_info)
+ klass.send :define_method, field_info[:name] do
+ if field_info[:name].to_sym == @setfield
+ @value
+ else
+ raise RuntimeError, "#{field_info[:name]} is not union's set field."
+ end
+ end
+
+ klass.send :define_method, "#{field_info[:name]}=" do |value|
+ Thrift.check_type(value, field_info, field_info[:name]) if Thrift.type_checking
+ @setfield = field_info[:name].to_sym
+ @value = value
+ end
+ end
+
+ def self.qmark_isset_method(klass, field_info)
+ klass.send :define_method, "#{field_info[:name]}?" do
+ get_set_field == field_info[:name].to_sym && !get_value.nil?
+ end
+ end
+
+ def self.generate_accessors(klass)
+ klass::FIELDS.values.each do |field_info|
+ field_accessor(klass, field_info)
+ qmark_isset_method(klass, field_info)
+ end
+ end
+
+ # get the symbol that indicates what the currently set field type is.
+ def get_set_field
+ @setfield
+ end
+
+ # get the current value of this union, regardless of what the set field is.
+ # generally, you should only use this method when you don't know in advance
+ # what field to expect.
+ def get_value
+ @value
+ end
+
+ def <=>(other)
+ if self.class == other.class
+ if get_set_field == other.get_set_field
+ if get_set_field.nil?
+ 0
+ else
+ get_value <=> other.get_value
+ end
+ else
+ if get_set_field && other.get_set_field.nil?
+ -1
+ elsif get_set_field.nil? && other.get_set_field
+ 1
+ elsif get_set_field.nil? && other.get_set_field.nil?
+ 0
+ else
+ name_to_id(get_set_field.to_s) <=> name_to_id(other.get_set_field.to_s)
+ end
+ end
+ else
+ self.class <=> other.class
+ end
+ end
+
+ protected
+
+ def handle_message(iprot, fid, ftype)
+ field = struct_fields[fid]
+ if field and field[:type] == ftype
+ @value = read_field(iprot, field)
+ name = field[:name].to_sym
+ @setfield = name
+ else
+ iprot.skip(ftype)
+ end
+ end
+ end
+end
diff --git a/debian/gems-compat/thrift-0.11.0.0/spec/BaseService.thrift b/debian/gems-compat/thrift-0.11.0.0/spec/BaseService.thrift
new file mode 100644
index 0000000000..5c7d32a6ce
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/spec/BaseService.thrift
@@ -0,0 +1,27 @@
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+namespace rb Base
+
+struct Hello {
+ 1: string greeting = "hello world"
+}
+
+service BaseService {
+ Hello greeting(1:bool english)
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/spec/ExtendedService.thrift b/debian/gems-compat/thrift-0.11.0.0/spec/ExtendedService.thrift
new file mode 100644
index 0000000000..1a6b705aaa
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/spec/ExtendedService.thrift
@@ -0,0 +1,25 @@
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+namespace rb Extended
+
+include "BaseService.thrift"
+
+service ExtendedService extends BaseService.BaseService {
+ void ping()
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/spec/Referenced.thrift b/debian/gems-compat/thrift-0.11.0.0/spec/Referenced.thrift
new file mode 100644
index 0000000000..98f183fe07
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/spec/Referenced.thrift
@@ -0,0 +1,44 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+namespace rb OtherNamespace
+
+enum SomeEnum {
+ ONE
+ TWO
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/spec/ThriftNamespacedSpec.thrift b/debian/gems-compat/thrift-0.11.0.0/spec/ThriftNamespacedSpec.thrift
new file mode 100644
index 0000000000..02f28895ac
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/spec/ThriftNamespacedSpec.thrift
@@ -0,0 +1,53 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+namespace rb NamespacedSpecNamespace
+
+include "Referenced.thrift"
+
+struct Hello {
+ 1: string greeting = "hello world"
+}
+
+service NamespacedNonblockingService {
+ Hello greeting(1:bool english)
+ bool block()
+ oneway void unblock(1:i32 n)
+ oneway void shutdown()
+ void sleep(1:double seconds)
+}
diff --git a/debian/gems-compat/thrift-0.11.0.0/spec/ThriftSpec.thrift b/debian/gems-compat/thrift-0.11.0.0/spec/ThriftSpec.thrift
new file mode 100644
index 0000000000..b42481b32d
--- /dev/null
+++ b/debian/gems-compat/thrift-0.11.0.0/spec/ThriftSpec.thrift
@@ -0,0 +1,183 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+#
+# Licensed to the Apache Software Foundation (ASF) under one
+# or more contributor license agreements. See the NOTICE file
+# distributed with this work for additional information
+# regarding copyright ownership. The ASF licenses this file
+# to you under the Apache License, Version 2.0 (the
+# "License"); you may not use this file except in compliance
+# with the License. You may obtain a copy of the License at
+#
+# http://www.apache.org/licenses/LICENSE-2.0
+#
+# Unless required by applicable law or agreed to in writing,
+# software distributed under the License is distributed on an
+# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+# KIND, either express or implied. See the License for the
+# specific language governing permissions and limitations
+# under the License.
+#
+
+namespace rb SpecNamespace
+
+struct Hello {
+ 1: string greeting = "hello world"
+}
+
+enum SomeEnum {
+ ONE
+ TWO
+}
+
+struct StructWithSomeEnum {
+ 1: SomeEnum some_enum;
+}
+
+union TestUnion {
+ /**
+ * A doc string
+ */
+ 1: string string_field;
+ 2: i32 i32_field;
+ 3: i32 other_i32_field;
+ 4: SomeEnum enum_field;
+ 5: binary binary_field;
+}
+
+struct Foo {
+ 1: i32 simple = 53,
+ 2: string words = "words",
+ 3: Hello hello = {'greeting' : "hello, world!"},
+ 4: list ints = [1, 2, 2, 3],
+ 5: map> complex,
+ 6: set shorts = [5, 17, 239],
+ 7: optional string opt_string
+ 8: bool my_bool
+}
+
+struct Foo2 {
+ 1: binary my_binary
+}
+
+struct BoolStruct {
+ 1: bool yesno = 1
+}
+
+struct SimpleList {
+ 1: list bools,
+ 2: list bytes,
+ 3: list i16s,
+ 4: list i32s,
+ 5: list i64s,
+ 6: list doubles,
+ 7: list strings,
+ 8: list