/src/thrift/lib/rs/src/protocol/binary.rs
Line | Count | Source |
1 | | // Licensed to the Apache Software Foundation (ASF) under one |
2 | | // or more contributor license agreements. See the NOTICE file |
3 | | // distributed with this work for additional information |
4 | | // regarding copyright ownership. The ASF licenses this file |
5 | | // to you under the Apache License, Version 2.0 (the |
6 | | // "License"); you may not use this file except in compliance |
7 | | // with the License. You may obtain a copy of the License at |
8 | | // |
9 | | // http://www.apache.org/licenses/LICENSE-2.0 |
10 | | // |
11 | | // Unless required by applicable law or agreed to in writing, |
12 | | // software distributed under the License is distributed on an |
13 | | // "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY |
14 | | // KIND, either express or implied. See the License for the |
15 | | // specific language governing permissions and limitations |
16 | | // under the License. |
17 | | |
18 | | use byteorder::{BigEndian, ByteOrder, ReadBytesExt, WriteBytesExt}; |
19 | | use std::convert::{From, TryFrom}; |
20 | | |
21 | | use super::{ |
22 | | TFieldIdentifier, TInputProtocol, TInputProtocolFactory, TListIdentifier, TMapIdentifier, |
23 | | TMessageIdentifier, TMessageType, |
24 | | }; |
25 | | use super::{TOutputProtocol, TOutputProtocolFactory, TSetIdentifier, TStructIdentifier, TType}; |
26 | | use crate::transport::{TReadTransport, TWriteTransport}; |
27 | | use crate::{ProtocolError, ProtocolErrorKind, TConfiguration}; |
28 | | |
29 | | const BINARY_PROTOCOL_VERSION_1: u32 = 0x8001_0000; |
30 | | |
31 | | /// Read messages encoded in the Thrift simple binary encoding. |
32 | | /// |
33 | | /// There are two available modes: `strict` and `non-strict`, where the |
34 | | /// `non-strict` version does not check for the protocol version in the |
35 | | /// received message header. |
36 | | /// |
37 | | /// # Examples |
38 | | /// |
39 | | /// Create and use a `TBinaryInputProtocol`. |
40 | | /// |
41 | | /// ```no_run |
42 | | /// use thrift::protocol::{TBinaryInputProtocol, TInputProtocol}; |
43 | | /// use thrift::transport::TTcpChannel; |
44 | | /// |
45 | | /// let mut channel = TTcpChannel::new(); |
46 | | /// channel.open("localhost:9090").unwrap(); |
47 | | /// |
48 | | /// let mut protocol = TBinaryInputProtocol::new(channel, true); |
49 | | /// |
50 | | /// let recvd_bool = protocol.read_bool().unwrap(); |
51 | | /// let recvd_string = protocol.read_string().unwrap(); |
52 | | /// ``` |
53 | | #[derive(Debug)] |
54 | | pub struct TBinaryInputProtocol<T> |
55 | | where |
56 | | T: TReadTransport, |
57 | | { |
58 | | strict: bool, |
59 | | pub transport: T, // FIXME: shouldn't be public |
60 | | config: TConfiguration, |
61 | | recursion_depth: usize, |
62 | | } |
63 | | |
64 | | impl<T> TBinaryInputProtocol<T> |
65 | | where |
66 | | T: TReadTransport, |
67 | | { |
68 | | /// Create a `TBinaryInputProtocol` that reads bytes from `transport`. |
69 | | /// |
70 | | /// Set `strict` to `true` if all incoming messages contain the protocol |
71 | | /// version number in the protocol header. |
72 | 0 | pub fn new(transport: T, strict: bool) -> Self { |
73 | 0 | Self::with_config(transport, strict, TConfiguration::default()) |
74 | 0 | } |
75 | | |
76 | 14.2k | pub fn with_config(transport: T, strict: bool, config: TConfiguration) -> Self { |
77 | 14.2k | TBinaryInputProtocol { |
78 | 14.2k | strict, |
79 | 14.2k | transport, |
80 | 14.2k | config, |
81 | 14.2k | recursion_depth: 0, |
82 | 14.2k | } |
83 | 14.2k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel>>::with_config Line | Count | Source | 76 | 6.24k | pub fn with_config(transport: T, strict: bool, config: TConfiguration) -> Self { | 77 | 6.24k | TBinaryInputProtocol { | 78 | 6.24k | strict, | 79 | 6.24k | transport, | 80 | 6.24k | config, | 81 | 6.24k | recursion_depth: 0, | 82 | 6.24k | } | 83 | 6.24k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>>>::with_config <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel>>::with_config Line | Count | Source | 76 | 8.00k | pub fn with_config(transport: T, strict: bool, config: TConfiguration) -> Self { | 77 | 8.00k | TBinaryInputProtocol { | 78 | 8.00k | strict, | 79 | 8.00k | transport, | 80 | 8.00k | config, | 81 | 8.00k | recursion_depth: 0, | 82 | 8.00k | } | 83 | 8.00k | } |
|
84 | | |
85 | 343k | fn check_recursion_depth(&self) -> crate::Result<()> { |
86 | 343k | if let Some(limit) = self.config.max_recursion_depth() { |
87 | 343k | if self.recursion_depth >= limit { |
88 | 10 | return Err(crate::Error::Protocol(ProtocolError::new( |
89 | 10 | ProtocolErrorKind::DepthLimit, |
90 | 10 | format!("Maximum recursion depth {} exceeded", limit), |
91 | 10 | ))); |
92 | 343k | } |
93 | 0 | } |
94 | 343k | Ok(()) |
95 | 343k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel>>::check_recursion_depth Line | Count | Source | 85 | 123k | fn check_recursion_depth(&self) -> crate::Result<()> { | 86 | 123k | if let Some(limit) = self.config.max_recursion_depth() { | 87 | 123k | if self.recursion_depth >= limit { | 88 | 6 | return Err(crate::Error::Protocol(ProtocolError::new( | 89 | 6 | ProtocolErrorKind::DepthLimit, | 90 | 6 | format!("Maximum recursion depth {} exceeded", limit), | 91 | 6 | ))); | 92 | 123k | } | 93 | 0 | } | 94 | 123k | Ok(()) | 95 | 123k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>>>::check_recursion_depth <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel>>::check_recursion_depth Line | Count | Source | 85 | 219k | fn check_recursion_depth(&self) -> crate::Result<()> { | 86 | 219k | if let Some(limit) = self.config.max_recursion_depth() { | 87 | 219k | if self.recursion_depth >= limit { | 88 | 4 | return Err(crate::Error::Protocol(ProtocolError::new( | 89 | 4 | ProtocolErrorKind::DepthLimit, | 90 | 4 | format!("Maximum recursion depth {} exceeded", limit), | 91 | 4 | ))); | 92 | 219k | } | 93 | 0 | } | 94 | 219k | Ok(()) | 95 | 219k | } |
|
96 | | } |
97 | | |
98 | | impl<T> TInputProtocol for TBinaryInputProtocol<T> |
99 | | where |
100 | | T: TReadTransport, |
101 | | { |
102 | | #[allow(clippy::collapsible_if)] |
103 | 0 | fn read_message_begin(&mut self) -> crate::Result<TMessageIdentifier> { |
104 | | // TODO: Once specialization is stable, call the message size tracking here |
105 | 0 | let mut first_bytes = vec![0; 4]; |
106 | 0 | self.transport.read_exact(&mut first_bytes[..])?; |
107 | | |
108 | | // the thrift version header is intentionally negative |
109 | | // so the first check we'll do is see if the sign bit is set |
110 | | // and if so - assume it's the protocol-version header |
111 | 0 | if (first_bytes[0] & 0x80) != 0 { |
112 | | // apparently we got a protocol-version header - check |
113 | | // it, and if it matches, read the rest of the fields |
114 | 0 | if first_bytes[0..2] != [0x80, 0x01] { |
115 | 0 | Err(crate::Error::Protocol(ProtocolError { |
116 | 0 | kind: ProtocolErrorKind::BadVersion, |
117 | 0 | message: format!("received bad version: {:?}", &first_bytes[0..2]), |
118 | 0 | })) |
119 | | } else { |
120 | 0 | let message_type: TMessageType = TryFrom::try_from(first_bytes[3])?; |
121 | 0 | let name = self.read_string()?; |
122 | 0 | let sequence_number = self.read_i32()?; |
123 | 0 | Ok(TMessageIdentifier::new(name, message_type, sequence_number)) |
124 | | } |
125 | | } else { |
126 | | // apparently we didn't get a protocol-version header, |
127 | | // which happens if the sender is not using the strict protocol |
128 | 0 | if self.strict { |
129 | | // we're in strict mode however, and that always |
130 | | // requires the protocol-version header to be written first |
131 | 0 | Err(crate::Error::Protocol(ProtocolError { |
132 | 0 | kind: ProtocolErrorKind::BadVersion, |
133 | 0 | message: format!("received bad version: {:?}", &first_bytes[0..2]), |
134 | 0 | })) |
135 | | } else { |
136 | | // in the non-strict version the first message field |
137 | | // is the message name. strings (byte arrays) are length-prefixed, |
138 | | // so we've just read the length in the first 4 bytes |
139 | 0 | let name_size = BigEndian::read_i32(&first_bytes) as usize; |
140 | 0 | if let Some(max_size) = self.config.max_string_size() { |
141 | 0 | if name_size > max_size { |
142 | 0 | return Err(crate::Error::Protocol(ProtocolError::new( |
143 | 0 | ProtocolErrorKind::SizeLimit, |
144 | 0 | format!( |
145 | 0 | "Message name size {} exceeds maximum allowed size of {}", |
146 | 0 | name_size, max_size |
147 | 0 | ), |
148 | 0 | ))); |
149 | 0 | } |
150 | 0 | } |
151 | 0 | let mut name_buf: Vec<u8> = vec![0; name_size]; |
152 | 0 | self.transport.read_exact(&mut name_buf)?; |
153 | 0 | let name = String::from_utf8(name_buf)?; |
154 | | |
155 | | // read the rest of the fields |
156 | 0 | let message_type: TMessageType = self.read_byte().and_then(TryFrom::try_from)?; |
157 | 0 | let sequence_number = self.read_i32()?; |
158 | 0 | Ok(TMessageIdentifier::new(name, message_type, sequence_number)) |
159 | | } |
160 | | } |
161 | 0 | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_message_begin Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_message_begin Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_message_begin |
162 | | |
163 | 0 | fn read_message_end(&mut self) -> crate::Result<()> { |
164 | 0 | Ok(()) |
165 | 0 | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_message_end Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_message_end Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_message_end |
166 | | |
167 | 343k | fn read_struct_begin(&mut self) -> crate::Result<Option<TStructIdentifier>> { |
168 | 343k | self.check_recursion_depth()?; |
169 | 343k | self.recursion_depth += 1; |
170 | 343k | Ok(None) |
171 | 343k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_struct_begin Line | Count | Source | 167 | 123k | fn read_struct_begin(&mut self) -> crate::Result<Option<TStructIdentifier>> { | 168 | 123k | self.check_recursion_depth()?; | 169 | 123k | self.recursion_depth += 1; | 170 | 123k | Ok(None) | 171 | 123k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_struct_begin <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_struct_begin Line | Count | Source | 167 | 219k | fn read_struct_begin(&mut self) -> crate::Result<Option<TStructIdentifier>> { | 168 | 219k | self.check_recursion_depth()?; | 169 | 219k | self.recursion_depth += 1; | 170 | 219k | Ok(None) | 171 | 219k | } |
|
172 | | |
173 | 321k | fn read_struct_end(&mut self) -> crate::Result<()> { |
174 | 321k | self.recursion_depth -= 1; |
175 | 321k | Ok(()) |
176 | 321k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_struct_end Line | Count | Source | 173 | 111k | fn read_struct_end(&mut self) -> crate::Result<()> { | 174 | 111k | self.recursion_depth -= 1; | 175 | 111k | Ok(()) | 176 | 111k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_struct_end <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_struct_end Line | Count | Source | 173 | 209k | fn read_struct_end(&mut self) -> crate::Result<()> { | 174 | 209k | self.recursion_depth -= 1; | 175 | 209k | Ok(()) | 176 | 209k | } |
|
177 | | |
178 | 889k | fn read_field_begin(&mut self) -> crate::Result<TFieldIdentifier> { |
179 | 889k | let field_type_byte = self.read_byte()?; |
180 | 884k | let field_type = field_type_from_u8(field_type_byte)?; |
181 | 884k | let id = match field_type { |
182 | 321k | TType::Stop => Ok(0), |
183 | 563k | _ => self.read_i16(), |
184 | 317 | }?; |
185 | 884k | Ok(TFieldIdentifier::new::<Option<String>, String, i16>( |
186 | 884k | None, field_type, id, |
187 | 884k | )) |
188 | 889k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_field_begin Line | Count | Source | 178 | 372k | fn read_field_begin(&mut self) -> crate::Result<TFieldIdentifier> { | 179 | 372k | let field_type_byte = self.read_byte()?; | 180 | 369k | let field_type = field_type_from_u8(field_type_byte)?; | 181 | 369k | let id = match field_type { | 182 | 111k | TType::Stop => Ok(0), | 183 | 257k | _ => self.read_i16(), | 184 | 160 | }?; | 185 | 369k | Ok(TFieldIdentifier::new::<Option<String>, String, i16>( | 186 | 369k | None, field_type, id, | 187 | 369k | )) | 188 | 372k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_field_begin <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_field_begin Line | Count | Source | 178 | 517k | fn read_field_begin(&mut self) -> crate::Result<TFieldIdentifier> { | 179 | 517k | let field_type_byte = self.read_byte()?; | 180 | 515k | let field_type = field_type_from_u8(field_type_byte)?; | 181 | 514k | let id = match field_type { | 182 | 209k | TType::Stop => Ok(0), | 183 | 305k | _ => self.read_i16(), | 184 | 157 | }?; | 185 | 514k | Ok(TFieldIdentifier::new::<Option<String>, String, i16>( | 186 | 514k | None, field_type, id, | 187 | 514k | )) | 188 | 517k | } |
|
189 | | |
190 | 532k | fn read_field_end(&mut self) -> crate::Result<()> { |
191 | 532k | Ok(()) |
192 | 532k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_field_end Line | Count | Source | 190 | 239k | fn read_field_end(&mut self) -> crate::Result<()> { | 191 | 239k | Ok(()) | 192 | 239k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_field_end <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_field_end Line | Count | Source | 190 | 292k | fn read_field_end(&mut self) -> crate::Result<()> { | 191 | 292k | Ok(()) | 192 | 292k | } |
|
193 | | |
194 | 2.55M | fn read_bytes(&mut self) -> crate::Result<Vec<u8>> { |
195 | 2.55M | let num_bytes = self.transport.read_i32::<BigEndian>()?; |
196 | | |
197 | 2.55M | if num_bytes < 0 { |
198 | 120 | return Err(crate::Error::Protocol(ProtocolError::new( |
199 | 120 | ProtocolErrorKind::NegativeSize, |
200 | 120 | format!("Negative byte array size: {}", num_bytes), |
201 | 120 | ))); |
202 | 2.55M | } |
203 | | |
204 | 2.55M | if let Some(max_size) = self.config.max_string_size() { |
205 | 2.55M | if num_bytes as usize > max_size { |
206 | 396 | return Err(crate::Error::Protocol(ProtocolError::new( |
207 | 396 | ProtocolErrorKind::SizeLimit, |
208 | 396 | format!( |
209 | 396 | "Byte array size {} exceeds maximum allowed size of {}", |
210 | 396 | num_bytes, max_size |
211 | 396 | ), |
212 | 396 | ))); |
213 | 2.55M | } |
214 | 0 | } |
215 | | |
216 | 2.55M | let mut buf = vec![0u8; num_bytes as usize]; |
217 | 2.55M | self.transport |
218 | 2.55M | .read_exact(&mut buf) |
219 | 2.55M | .map(|_| buf) |
220 | 2.55M | .map_err(From::from) |
221 | 2.55M | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_bytes Line | Count | Source | 194 | 1.36M | fn read_bytes(&mut self) -> crate::Result<Vec<u8>> { | 195 | 1.36M | let num_bytes = self.transport.read_i32::<BigEndian>()?; | 196 | | | 197 | 1.36M | if num_bytes < 0 { | 198 | 57 | return Err(crate::Error::Protocol(ProtocolError::new( | 199 | 57 | ProtocolErrorKind::NegativeSize, | 200 | 57 | format!("Negative byte array size: {}", num_bytes), | 201 | 57 | ))); | 202 | 1.36M | } | 203 | | | 204 | 1.36M | if let Some(max_size) = self.config.max_string_size() { | 205 | 1.36M | if num_bytes as usize > max_size { | 206 | 226 | return Err(crate::Error::Protocol(ProtocolError::new( | 207 | 226 | ProtocolErrorKind::SizeLimit, | 208 | 226 | format!( | 209 | 226 | "Byte array size {} exceeds maximum allowed size of {}", | 210 | 226 | num_bytes, max_size | 211 | 226 | ), | 212 | 226 | ))); | 213 | 1.36M | } | 214 | 0 | } | 215 | | | 216 | 1.36M | let mut buf = vec![0u8; num_bytes as usize]; | 217 | 1.36M | self.transport | 218 | 1.36M | .read_exact(&mut buf) | 219 | 1.36M | .map(|_| buf) | 220 | 1.36M | .map_err(From::from) | 221 | 1.36M | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_bytes <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_bytes Line | Count | Source | 194 | 1.19M | fn read_bytes(&mut self) -> crate::Result<Vec<u8>> { | 195 | 1.19M | let num_bytes = self.transport.read_i32::<BigEndian>()?; | 196 | | | 197 | 1.18M | if num_bytes < 0 { | 198 | 63 | return Err(crate::Error::Protocol(ProtocolError::new( | 199 | 63 | ProtocolErrorKind::NegativeSize, | 200 | 63 | format!("Negative byte array size: {}", num_bytes), | 201 | 63 | ))); | 202 | 1.18M | } | 203 | | | 204 | 1.18M | if let Some(max_size) = self.config.max_string_size() { | 205 | 1.18M | if num_bytes as usize > max_size { | 206 | 170 | return Err(crate::Error::Protocol(ProtocolError::new( | 207 | 170 | ProtocolErrorKind::SizeLimit, | 208 | 170 | format!( | 209 | 170 | "Byte array size {} exceeds maximum allowed size of {}", | 210 | 170 | num_bytes, max_size | 211 | 170 | ), | 212 | 170 | ))); | 213 | 1.18M | } | 214 | 0 | } | 215 | | | 216 | 1.18M | let mut buf = vec![0u8; num_bytes as usize]; | 217 | 1.18M | self.transport | 218 | 1.18M | .read_exact(&mut buf) | 219 | 1.18M | .map(|_| buf) | 220 | 1.18M | .map_err(From::from) | 221 | 1.19M | } |
|
222 | | |
223 | 90.3k | fn read_bool(&mut self) -> crate::Result<bool> { |
224 | 90.3k | let b = self.read_i8()?; |
225 | 90.1k | match b { |
226 | 22.8k | 0 => Ok(false), |
227 | 67.3k | _ => Ok(true), |
228 | | } |
229 | 90.3k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_bool Line | Count | Source | 223 | 60.5k | fn read_bool(&mut self) -> crate::Result<bool> { | 224 | 60.5k | let b = self.read_i8()?; | 225 | 60.5k | match b { | 226 | 11.3k | 0 => Ok(false), | 227 | 49.1k | _ => Ok(true), | 228 | | } | 229 | 60.5k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_bool <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_bool Line | Count | Source | 223 | 29.7k | fn read_bool(&mut self) -> crate::Result<bool> { | 224 | 29.7k | let b = self.read_i8()?; | 225 | 29.6k | match b { | 226 | 11.4k | 0 => Ok(false), | 227 | 18.2k | _ => Ok(true), | 228 | | } | 229 | 29.7k | } |
|
230 | | |
231 | 132k | fn read_i8(&mut self) -> crate::Result<i8> { |
232 | 132k | self.transport.read_i8().map_err(From::from) |
233 | 132k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_i8 Line | Count | Source | 231 | 81.0k | fn read_i8(&mut self) -> crate::Result<i8> { | 232 | 81.0k | self.transport.read_i8().map_err(From::from) | 233 | 81.0k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_i8 <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_i8 Line | Count | Source | 231 | 51.5k | fn read_i8(&mut self) -> crate::Result<i8> { | 232 | 51.5k | self.transport.read_i8().map_err(From::from) | 233 | 51.5k | } |
|
234 | | |
235 | 575k | fn read_i16(&mut self) -> crate::Result<i16> { |
236 | 575k | self.transport.read_i16::<BigEndian>().map_err(From::from) |
237 | 575k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_i16 Line | Count | Source | 235 | 261k | fn read_i16(&mut self) -> crate::Result<i16> { | 236 | 261k | self.transport.read_i16::<BigEndian>().map_err(From::from) | 237 | 261k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_i16 <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_i16 Line | Count | Source | 235 | 313k | fn read_i16(&mut self) -> crate::Result<i16> { | 236 | 313k | self.transport.read_i16::<BigEndian>().map_err(From::from) | 237 | 313k | } |
|
238 | | |
239 | 2.32M | fn read_i32(&mut self) -> crate::Result<i32> { |
240 | 2.32M | self.transport.read_i32::<BigEndian>().map_err(From::from) |
241 | 2.32M | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_i32 Line | Count | Source | 239 | 1.07M | fn read_i32(&mut self) -> crate::Result<i32> { | 240 | 1.07M | self.transport.read_i32::<BigEndian>().map_err(From::from) | 241 | 1.07M | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_i32 <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_i32 Line | Count | Source | 239 | 1.25M | fn read_i32(&mut self) -> crate::Result<i32> { | 240 | 1.25M | self.transport.read_i32::<BigEndian>().map_err(From::from) | 241 | 1.25M | } |
|
242 | | |
243 | 1.61M | fn read_i64(&mut self) -> crate::Result<i64> { |
244 | 1.61M | self.transport.read_i64::<BigEndian>().map_err(From::from) |
245 | 1.61M | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_i64 Line | Count | Source | 243 | 768k | fn read_i64(&mut self) -> crate::Result<i64> { | 244 | 768k | self.transport.read_i64::<BigEndian>().map_err(From::from) | 245 | 768k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_i64 <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_i64 Line | Count | Source | 243 | 843k | fn read_i64(&mut self) -> crate::Result<i64> { | 244 | 843k | self.transport.read_i64::<BigEndian>().map_err(From::from) | 245 | 843k | } |
|
246 | | |
247 | 12.6k | fn read_double(&mut self) -> crate::Result<f64> { |
248 | 12.6k | self.transport.read_f64::<BigEndian>().map_err(From::from) |
249 | 12.6k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_double Line | Count | Source | 247 | 1.65k | fn read_double(&mut self) -> crate::Result<f64> { | 248 | 1.65k | self.transport.read_f64::<BigEndian>().map_err(From::from) | 249 | 1.65k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_double <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_double Line | Count | Source | 247 | 10.9k | fn read_double(&mut self) -> crate::Result<f64> { | 248 | 10.9k | self.transport.read_f64::<BigEndian>().map_err(From::from) | 249 | 10.9k | } |
|
250 | | |
251 | 9.99k | fn read_uuid(&mut self) -> crate::Result<uuid::Uuid> { |
252 | 9.99k | let mut buf = [0u8; 16]; |
253 | 9.99k | self.transport |
254 | 9.99k | .read_exact(&mut buf) |
255 | 9.99k | .map(|_| uuid::Uuid::from_bytes(buf)) <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_uuid::{closure#0}Line | Count | Source | 255 | 2.73k | .map(|_| uuid::Uuid::from_bytes(buf)) |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_uuid::{closure#0}<thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_uuid::{closure#0}Line | Count | Source | 255 | 7.21k | .map(|_| uuid::Uuid::from_bytes(buf)) |
|
256 | 9.99k | .map_err(From::from) |
257 | 9.99k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_uuid Line | Count | Source | 251 | 2.76k | fn read_uuid(&mut self) -> crate::Result<uuid::Uuid> { | 252 | 2.76k | let mut buf = [0u8; 16]; | 253 | 2.76k | self.transport | 254 | 2.76k | .read_exact(&mut buf) | 255 | 2.76k | .map(|_| uuid::Uuid::from_bytes(buf)) | 256 | 2.76k | .map_err(From::from) | 257 | 2.76k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_uuid <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_uuid Line | Count | Source | 251 | 7.23k | fn read_uuid(&mut self) -> crate::Result<uuid::Uuid> { | 252 | 7.23k | let mut buf = [0u8; 16]; | 253 | 7.23k | self.transport | 254 | 7.23k | .read_exact(&mut buf) | 255 | 7.23k | .map(|_| uuid::Uuid::from_bytes(buf)) | 256 | 7.23k | .map_err(From::from) | 257 | 7.23k | } |
|
258 | | |
259 | 2.52M | fn read_string(&mut self) -> crate::Result<String> { |
260 | 2.52M | let bytes = self.read_bytes()?; |
261 | 2.52M | String::from_utf8(bytes).map_err(From::from) |
262 | 2.52M | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_string Line | Count | Source | 259 | 1.35M | fn read_string(&mut self) -> crate::Result<String> { | 260 | 1.35M | let bytes = self.read_bytes()?; | 261 | 1.35M | String::from_utf8(bytes).map_err(From::from) | 262 | 1.35M | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_string <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_string Line | Count | Source | 259 | 1.17M | fn read_string(&mut self) -> crate::Result<String> { | 260 | 1.17M | let bytes = self.read_bytes()?; | 261 | 1.17M | String::from_utf8(bytes).map_err(From::from) | 262 | 1.17M | } |
|
263 | | |
264 | 173k | fn read_list_begin(&mut self) -> crate::Result<TListIdentifier> { |
265 | 173k | let element_type: TType = self.read_byte().and_then(field_type_from_u8)?; |
266 | 173k | let size = self.read_i32()?; |
267 | 173k | let min_element_size = self.min_serialized_size(element_type); |
268 | 173k | super::check_container_size(&self.config, size, min_element_size)?; |
269 | 173k | Ok(TListIdentifier::new(element_type, size)) |
270 | 173k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_list_begin Line | Count | Source | 264 | 81.2k | fn read_list_begin(&mut self) -> crate::Result<TListIdentifier> { | 265 | 81.2k | let element_type: TType = self.read_byte().and_then(field_type_from_u8)?; | 266 | 81.1k | let size = self.read_i32()?; | 267 | 81.1k | let min_element_size = self.min_serialized_size(element_type); | 268 | 81.1k | super::check_container_size(&self.config, size, min_element_size)?; | 269 | 81.0k | Ok(TListIdentifier::new(element_type, size)) | 270 | 81.2k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_list_begin <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_list_begin Line | Count | Source | 264 | 92.2k | fn read_list_begin(&mut self) -> crate::Result<TListIdentifier> { | 265 | 92.2k | let element_type: TType = self.read_byte().and_then(field_type_from_u8)?; | 266 | 92.2k | let size = self.read_i32()?; | 267 | 92.1k | let min_element_size = self.min_serialized_size(element_type); | 268 | 92.1k | super::check_container_size(&self.config, size, min_element_size)?; | 269 | 92.1k | Ok(TListIdentifier::new(element_type, size)) | 270 | 92.2k | } |
|
271 | | |
272 | 171k | fn read_list_end(&mut self) -> crate::Result<()> { |
273 | 171k | Ok(()) |
274 | 171k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_list_end Line | Count | Source | 272 | 80.4k | fn read_list_end(&mut self) -> crate::Result<()> { | 273 | 80.4k | Ok(()) | 274 | 80.4k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_list_end <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_list_end Line | Count | Source | 272 | 91.5k | fn read_list_end(&mut self) -> crate::Result<()> { | 273 | 91.5k | Ok(()) | 274 | 91.5k | } |
|
275 | | |
276 | 29.3k | fn read_set_begin(&mut self) -> crate::Result<TSetIdentifier> { |
277 | 29.3k | let element_type: TType = self.read_byte().and_then(field_type_from_u8)?; |
278 | 29.2k | let size = self.read_i32()?; |
279 | 29.2k | let min_element_size = self.min_serialized_size(element_type); |
280 | 29.2k | super::check_container_size(&self.config, size, min_element_size)?; |
281 | 29.1k | Ok(TSetIdentifier::new(element_type, size)) |
282 | 29.3k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_set_begin Line | Count | Source | 276 | 15.9k | fn read_set_begin(&mut self) -> crate::Result<TSetIdentifier> { | 277 | 15.9k | let element_type: TType = self.read_byte().and_then(field_type_from_u8)?; | 278 | 15.8k | let size = self.read_i32()?; | 279 | 15.8k | let min_element_size = self.min_serialized_size(element_type); | 280 | 15.8k | super::check_container_size(&self.config, size, min_element_size)?; | 281 | 15.7k | Ok(TSetIdentifier::new(element_type, size)) | 282 | 15.9k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_set_begin <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_set_begin Line | Count | Source | 276 | 13.4k | fn read_set_begin(&mut self) -> crate::Result<TSetIdentifier> { | 277 | 13.4k | let element_type: TType = self.read_byte().and_then(field_type_from_u8)?; | 278 | 13.4k | let size = self.read_i32()?; | 279 | 13.4k | let min_element_size = self.min_serialized_size(element_type); | 280 | 13.4k | super::check_container_size(&self.config, size, min_element_size)?; | 281 | 13.4k | Ok(TSetIdentifier::new(element_type, size)) | 282 | 13.4k | } |
|
283 | | |
284 | 27.4k | fn read_set_end(&mut self) -> crate::Result<()> { |
285 | 27.4k | Ok(()) |
286 | 27.4k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_set_end Line | Count | Source | 284 | 14.7k | fn read_set_end(&mut self) -> crate::Result<()> { | 285 | 14.7k | Ok(()) | 286 | 14.7k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_set_end <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_set_end Line | Count | Source | 284 | 12.6k | fn read_set_end(&mut self) -> crate::Result<()> { | 285 | 12.6k | Ok(()) | 286 | 12.6k | } |
|
287 | | |
288 | 40.6k | fn read_map_begin(&mut self) -> crate::Result<TMapIdentifier> { |
289 | 40.6k | let key_type: TType = self.read_byte().and_then(field_type_from_u8)?; |
290 | 40.4k | let value_type: TType = self.read_byte().and_then(field_type_from_u8)?; |
291 | 40.4k | let size = self.read_i32()?; |
292 | | |
293 | 40.3k | let key_min_size = self.min_serialized_size(key_type); |
294 | 40.3k | let value_min_size = self.min_serialized_size(value_type); |
295 | 40.3k | let element_size = key_min_size + value_min_size; |
296 | 40.3k | super::check_container_size(&self.config, size, element_size)?; |
297 | | |
298 | 40.3k | Ok(TMapIdentifier::new(key_type, value_type, size)) |
299 | 40.6k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_map_begin Line | Count | Source | 288 | 17.6k | fn read_map_begin(&mut self) -> crate::Result<TMapIdentifier> { | 289 | 17.6k | let key_type: TType = self.read_byte().and_then(field_type_from_u8)?; | 290 | 17.5k | let value_type: TType = self.read_byte().and_then(field_type_from_u8)?; | 291 | 17.5k | let size = self.read_i32()?; | 292 | | | 293 | 17.5k | let key_min_size = self.min_serialized_size(key_type); | 294 | 17.5k | let value_min_size = self.min_serialized_size(value_type); | 295 | 17.5k | let element_size = key_min_size + value_min_size; | 296 | 17.5k | super::check_container_size(&self.config, size, element_size)?; | 297 | | | 298 | 17.5k | Ok(TMapIdentifier::new(key_type, value_type, size)) | 299 | 17.6k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_map_begin <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_map_begin Line | Count | Source | 288 | 22.9k | fn read_map_begin(&mut self) -> crate::Result<TMapIdentifier> { | 289 | 22.9k | let key_type: TType = self.read_byte().and_then(field_type_from_u8)?; | 290 | 22.8k | let value_type: TType = self.read_byte().and_then(field_type_from_u8)?; | 291 | 22.8k | let size = self.read_i32()?; | 292 | | | 293 | 22.8k | let key_min_size = self.min_serialized_size(key_type); | 294 | 22.8k | let value_min_size = self.min_serialized_size(value_type); | 295 | 22.8k | let element_size = key_min_size + value_min_size; | 296 | 22.8k | super::check_container_size(&self.config, size, element_size)?; | 297 | | | 298 | 22.8k | Ok(TMapIdentifier::new(key_type, value_type, size)) | 299 | 22.9k | } |
|
300 | | |
301 | 37.7k | fn read_map_end(&mut self) -> crate::Result<()> { |
302 | 37.7k | Ok(()) |
303 | 37.7k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_map_end Line | Count | Source | 301 | 16.2k | fn read_map_end(&mut self) -> crate::Result<()> { | 302 | 16.2k | Ok(()) | 303 | 16.2k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_map_end <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_map_end Line | Count | Source | 301 | 21.5k | fn read_map_end(&mut self) -> crate::Result<()> { | 302 | 21.5k | Ok(()) | 303 | 21.5k | } |
|
304 | | |
305 | | // utility |
306 | | // |
307 | | |
308 | 1.17M | fn read_byte(&mut self) -> crate::Result<u8> { |
309 | 1.17M | self.transport.read_u8().map_err(From::from) |
310 | 1.17M | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_byte Line | Count | Source | 308 | 504k | fn read_byte(&mut self) -> crate::Result<u8> { | 309 | 504k | self.transport.read_u8().map_err(From::from) | 310 | 504k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::read_byte <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::read_byte Line | Count | Source | 308 | 668k | fn read_byte(&mut self) -> crate::Result<u8> { | 309 | 668k | self.transport.read_u8().map_err(From::from) | 310 | 668k | } |
|
311 | | |
312 | 283k | fn min_serialized_size(&self, field_type: TType) -> usize { |
313 | 283k | match field_type { |
314 | 166k | TType::Stop => 1, // 1 byte minimum |
315 | 11.3k | TType::Void => 1, // 1 byte minimum |
316 | 1.42k | TType::Bool => 1, // 1 byte |
317 | 948 | TType::I08 => 1, // 1 byte |
318 | 2.51k | TType::Double => 8, // 8 bytes |
319 | 363 | TType::I16 => 2, // 2 bytes |
320 | 26.3k | TType::I32 => 4, // 4 bytes |
321 | 11.3k | TType::I64 => 8, // 8 bytes |
322 | 31.4k | TType::String => 4, // 4 bytes for length prefix |
323 | 20.6k | TType::Struct => 1, // 1 byte minimum (stop field) |
324 | 1.62k | TType::Map => 4, // 4 bytes size |
325 | 928 | TType::Set => 4, // 4 bytes size |
326 | 7.82k | TType::List => 4, // 4 bytes size |
327 | 83 | TType::Uuid => 16, // 16 bytes |
328 | 0 | TType::Utf7 => 1, // 1 byte |
329 | | } |
330 | 283k | } <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::min_serialized_size Line | Count | Source | 312 | 132k | fn min_serialized_size(&self, field_type: TType) -> usize { | 313 | 132k | match field_type { | 314 | 84.5k | TType::Stop => 1, // 1 byte minimum | 315 | 4.47k | TType::Void => 1, // 1 byte minimum | 316 | 883 | TType::Bool => 1, // 1 byte | 317 | 376 | TType::I08 => 1, // 1 byte | 318 | 836 | TType::Double => 8, // 8 bytes | 319 | 166 | TType::I16 => 2, // 2 bytes | 320 | 7.44k | TType::I32 => 4, // 4 bytes | 321 | 7.74k | TType::I64 => 8, // 8 bytes | 322 | 12.2k | TType::String => 4, // 4 bytes for length prefix | 323 | 9.19k | TType::Struct => 1, // 1 byte minimum (stop field) | 324 | 639 | TType::Map => 4, // 4 bytes size | 325 | 575 | TType::Set => 4, // 4 bytes size | 326 | 2.83k | TType::List => 4, // 4 bytes size | 327 | 52 | TType::Uuid => 16, // 16 bytes | 328 | 0 | TType::Utf7 => 1, // 1 byte | 329 | | } | 330 | 132k | } |
Unexecuted instantiation: <thrift::protocol::binary::TBinaryInputProtocol<alloc::boxed::Box<dyn thrift::transport::TReadTransport + core::marker::Send>> as thrift::protocol::TInputProtocol>::min_serialized_size <thrift::protocol::binary::TBinaryInputProtocol<thrift::transport::mem::TBufferChannel> as thrift::protocol::TInputProtocol>::min_serialized_size Line | Count | Source | 312 | 151k | fn min_serialized_size(&self, field_type: TType) -> usize { | 313 | 151k | match field_type { | 314 | 81.8k | TType::Stop => 1, // 1 byte minimum | 315 | 6.92k | TType::Void => 1, // 1 byte minimum | 316 | 540 | TType::Bool => 1, // 1 byte | 317 | 572 | TType::I08 => 1, // 1 byte | 318 | 1.67k | TType::Double => 8, // 8 bytes | 319 | 197 | TType::I16 => 2, // 2 bytes | 320 | 18.9k | TType::I32 => 4, // 4 bytes | 321 | 3.61k | TType::I64 => 8, // 8 bytes | 322 | 19.1k | TType::String => 4, // 4 bytes for length prefix | 323 | 11.4k | TType::Struct => 1, // 1 byte minimum (stop field) | 324 | 985 | TType::Map => 4, // 4 bytes size | 325 | 353 | TType::Set => 4, // 4 bytes size | 326 | 4.98k | TType::List => 4, // 4 bytes size | 327 | 31 | TType::Uuid => 16, // 16 bytes | 328 | 0 | TType::Utf7 => 1, // 1 byte | 329 | | } | 330 | 151k | } |
|
331 | | } |
332 | | |
333 | | /// Factory for creating instances of `TBinaryInputProtocol`. |
334 | | #[derive(Default)] |
335 | | pub struct TBinaryInputProtocolFactory; |
336 | | |
337 | | impl TBinaryInputProtocolFactory { |
338 | | /// Create a `TBinaryInputProtocolFactory`. |
339 | 0 | pub fn new() -> TBinaryInputProtocolFactory { |
340 | 0 | TBinaryInputProtocolFactory {} |
341 | 0 | } |
342 | | } |
343 | | |
344 | | impl TInputProtocolFactory for TBinaryInputProtocolFactory { |
345 | 0 | fn create(&self, transport: Box<dyn TReadTransport + Send>) -> Box<dyn TInputProtocol + Send> { |
346 | 0 | Box::new(TBinaryInputProtocol::new(transport, true)) |
347 | 0 | } |
348 | | } |
349 | | |
350 | | /// Write messages using the Thrift simple binary encoding. |
351 | | /// |
352 | | /// There are two available modes: `strict` and `non-strict`, where the |
353 | | /// `strict` version writes the protocol version number in the outgoing message |
354 | | /// header and the `non-strict` version does not. |
355 | | /// |
356 | | /// # Examples |
357 | | /// |
358 | | /// Create and use a `TBinaryOutputProtocol`. |
359 | | /// |
360 | | /// ```no_run |
361 | | /// use thrift::protocol::{TBinaryOutputProtocol, TOutputProtocol}; |
362 | | /// use thrift::transport::TTcpChannel; |
363 | | /// |
364 | | /// let mut channel = TTcpChannel::new(); |
365 | | /// channel.open("localhost:9090").unwrap(); |
366 | | /// |
367 | | /// let mut protocol = TBinaryOutputProtocol::new(channel, true); |
368 | | /// |
369 | | /// protocol.write_bool(true).unwrap(); |
370 | | /// protocol.write_string("test_string").unwrap(); |
371 | | /// ``` |
372 | | #[derive(Debug)] |
373 | | pub struct TBinaryOutputProtocol<T> |
374 | | where |
375 | | T: TWriteTransport, |
376 | | { |
377 | | strict: bool, |
378 | | pub transport: T, // FIXME: do not make public; only public for testing! |
379 | | config: TConfiguration, |
380 | | recursion_depth: usize, |
381 | | } |
382 | | |
383 | | impl<T> TBinaryOutputProtocol<T> |
384 | | where |
385 | | T: TWriteTransport, |
386 | | { |
387 | | /// Create a `TBinaryOutputProtocol` that writes bytes to `transport`. |
388 | | /// |
389 | | /// Set `strict` to `true` if all outgoing messages should contain the |
390 | | /// protocol version number in the protocol header. |
391 | 2.06k | pub fn new(transport: T, strict: bool) -> TBinaryOutputProtocol<T> { |
392 | 2.06k | Self::with_config(transport, strict, TConfiguration::default()) |
393 | 2.06k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>>>::new <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel>>::new Line | Count | Source | 391 | 2.06k | pub fn new(transport: T, strict: bool) -> TBinaryOutputProtocol<T> { | 392 | 2.06k | Self::with_config(transport, strict, TConfiguration::default()) | 393 | 2.06k | } |
|
394 | | |
395 | 2.06k | pub fn with_config( |
396 | 2.06k | transport: T, |
397 | 2.06k | strict: bool, |
398 | 2.06k | config: TConfiguration, |
399 | 2.06k | ) -> TBinaryOutputProtocol<T> { |
400 | 2.06k | TBinaryOutputProtocol { |
401 | 2.06k | strict, |
402 | 2.06k | transport, |
403 | 2.06k | config, |
404 | 2.06k | recursion_depth: 0, |
405 | 2.06k | } |
406 | 2.06k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>>>::with_config <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel>>::with_config Line | Count | Source | 395 | 2.06k | pub fn with_config( | 396 | 2.06k | transport: T, | 397 | 2.06k | strict: bool, | 398 | 2.06k | config: TConfiguration, | 399 | 2.06k | ) -> TBinaryOutputProtocol<T> { | 400 | 2.06k | TBinaryOutputProtocol { | 401 | 2.06k | strict, | 402 | 2.06k | transport, | 403 | 2.06k | config, | 404 | 2.06k | recursion_depth: 0, | 405 | 2.06k | } | 406 | 2.06k | } |
|
407 | | |
408 | 51.5k | fn check_recursion_depth(&self) -> crate::Result<()> { |
409 | 51.5k | if let Some(limit) = self.config.max_recursion_depth() { |
410 | 51.5k | if self.recursion_depth >= limit { |
411 | 0 | return Err(crate::Error::Protocol(ProtocolError::new( |
412 | 0 | ProtocolErrorKind::DepthLimit, |
413 | 0 | format!("Maximum recursion depth {} exceeded", limit), |
414 | 0 | ))); |
415 | 51.5k | } |
416 | 0 | } |
417 | 51.5k | Ok(()) |
418 | 51.5k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>>>::check_recursion_depth <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel>>::check_recursion_depth Line | Count | Source | 408 | 51.5k | fn check_recursion_depth(&self) -> crate::Result<()> { | 409 | 51.5k | if let Some(limit) = self.config.max_recursion_depth() { | 410 | 51.5k | if self.recursion_depth >= limit { | 411 | 0 | return Err(crate::Error::Protocol(ProtocolError::new( | 412 | 0 | ProtocolErrorKind::DepthLimit, | 413 | 0 | format!("Maximum recursion depth {} exceeded", limit), | 414 | 0 | ))); | 415 | 51.5k | } | 416 | 0 | } | 417 | 51.5k | Ok(()) | 418 | 51.5k | } |
|
419 | | } |
420 | | |
421 | | impl<T> TOutputProtocol for TBinaryOutputProtocol<T> |
422 | | where |
423 | | T: TWriteTransport, |
424 | | { |
425 | 0 | fn write_message_begin(&mut self, identifier: &TMessageIdentifier) -> crate::Result<()> { |
426 | 0 | if self.strict { |
427 | 0 | let message_type: u8 = identifier.message_type.into(); |
428 | 0 | let header = BINARY_PROTOCOL_VERSION_1 | (message_type as u32); |
429 | 0 | self.transport.write_u32::<BigEndian>(header)?; |
430 | 0 | self.write_string(&identifier.name)?; |
431 | 0 | self.write_i32(identifier.sequence_number) |
432 | | } else { |
433 | 0 | self.write_string(&identifier.name)?; |
434 | 0 | self.write_byte(identifier.message_type.into())?; |
435 | 0 | self.write_i32(identifier.sequence_number) |
436 | | } |
437 | 0 | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_message_begin Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_message_begin |
438 | | |
439 | 0 | fn write_message_end(&mut self) -> crate::Result<()> { |
440 | 0 | Ok(()) |
441 | 0 | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_message_end Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_message_end |
442 | | |
443 | 51.5k | fn write_struct_begin(&mut self, _: &TStructIdentifier) -> crate::Result<()> { |
444 | 51.5k | self.check_recursion_depth()?; |
445 | 51.5k | self.recursion_depth += 1; |
446 | 51.5k | Ok(()) |
447 | 51.5k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_struct_begin <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_struct_begin Line | Count | Source | 443 | 51.5k | fn write_struct_begin(&mut self, _: &TStructIdentifier) -> crate::Result<()> { | 444 | 51.5k | self.check_recursion_depth()?; | 445 | 51.5k | self.recursion_depth += 1; | 446 | 51.5k | Ok(()) | 447 | 51.5k | } |
|
448 | | |
449 | 46.6k | fn write_struct_end(&mut self) -> crate::Result<()> { |
450 | 46.6k | self.recursion_depth -= 1; |
451 | 46.6k | Ok(()) |
452 | 46.6k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_struct_end <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_struct_end Line | Count | Source | 449 | 46.6k | fn write_struct_end(&mut self) -> crate::Result<()> { | 450 | 46.6k | self.recursion_depth -= 1; | 451 | 46.6k | Ok(()) | 452 | 46.6k | } |
|
453 | | |
454 | 188k | fn write_field_begin(&mut self, identifier: &TFieldIdentifier) -> crate::Result<()> { |
455 | 188k | if identifier.id.is_none() && identifier.field_type != TType::Stop { |
456 | 0 | return Err(crate::Error::Protocol(ProtocolError { |
457 | 0 | kind: ProtocolErrorKind::Unknown, |
458 | 0 | message: format!( |
459 | 0 | "cannot write identifier {:?} without sequence number", |
460 | 0 | &identifier |
461 | 0 | ), |
462 | 0 | })); |
463 | 188k | } |
464 | | |
465 | 188k | self.write_byte(field_type_to_u8(identifier.field_type))?; |
466 | 188k | if let Some(id) = identifier.id { |
467 | 188k | self.write_i16(id) |
468 | | } else { |
469 | 0 | Ok(()) |
470 | | } |
471 | 188k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_field_begin <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_field_begin Line | Count | Source | 454 | 188k | fn write_field_begin(&mut self, identifier: &TFieldIdentifier) -> crate::Result<()> { | 455 | 188k | if identifier.id.is_none() && identifier.field_type != TType::Stop { | 456 | 0 | return Err(crate::Error::Protocol(ProtocolError { | 457 | 0 | kind: ProtocolErrorKind::Unknown, | 458 | 0 | message: format!( | 459 | 0 | "cannot write identifier {:?} without sequence number", | 460 | 0 | &identifier | 461 | 0 | ), | 462 | 0 | })); | 463 | 188k | } | 464 | | | 465 | 188k | self.write_byte(field_type_to_u8(identifier.field_type))?; | 466 | 188k | if let Some(id) = identifier.id { | 467 | 188k | self.write_i16(id) | 468 | | } else { | 469 | 0 | Ok(()) | 470 | | } | 471 | 188k | } |
|
472 | | |
473 | 183k | fn write_field_end(&mut self) -> crate::Result<()> { |
474 | 183k | Ok(()) |
475 | 183k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_field_end <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_field_end Line | Count | Source | 473 | 183k | fn write_field_end(&mut self) -> crate::Result<()> { | 474 | 183k | Ok(()) | 475 | 183k | } |
|
476 | | |
477 | 46.7k | fn write_field_stop(&mut self) -> crate::Result<()> { |
478 | 46.7k | self.write_byte(field_type_to_u8(TType::Stop)) |
479 | 46.7k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_field_stop <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_field_stop Line | Count | Source | 477 | 46.7k | fn write_field_stop(&mut self) -> crate::Result<()> { | 478 | 46.7k | self.write_byte(field_type_to_u8(TType::Stop)) | 479 | 46.7k | } |
|
480 | | |
481 | 49.9k | fn write_bytes(&mut self, b: &[u8]) -> crate::Result<()> { |
482 | 49.9k | self.write_i32(b.len() as i32)?; |
483 | 49.8k | self.transport.write_all(b).map_err(From::from) |
484 | 49.9k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_bytes <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_bytes Line | Count | Source | 481 | 49.9k | fn write_bytes(&mut self, b: &[u8]) -> crate::Result<()> { | 482 | 49.9k | self.write_i32(b.len() as i32)?; | 483 | 49.8k | self.transport.write_all(b).map_err(From::from) | 484 | 49.9k | } |
|
485 | | |
486 | 16.0k | fn write_bool(&mut self, b: bool) -> crate::Result<()> { |
487 | 16.0k | if b { |
488 | 1.65k | self.write_i8(1) |
489 | | } else { |
490 | 14.4k | self.write_i8(0) |
491 | | } |
492 | 16.0k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_bool <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_bool Line | Count | Source | 486 | 16.0k | fn write_bool(&mut self, b: bool) -> crate::Result<()> { | 487 | 16.0k | if b { | 488 | 1.65k | self.write_i8(1) | 489 | | } else { | 490 | 14.4k | self.write_i8(0) | 491 | | } | 492 | 16.0k | } |
|
493 | | |
494 | 30.4k | fn write_i8(&mut self, i: i8) -> crate::Result<()> { |
495 | 30.4k | self.transport.write_i8(i).map_err(From::from) |
496 | 30.4k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_i8 <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_i8 Line | Count | Source | 494 | 30.4k | fn write_i8(&mut self, i: i8) -> crate::Result<()> { | 495 | 30.4k | self.transport.write_i8(i).map_err(From::from) | 496 | 30.4k | } |
|
497 | | |
498 | 202k | fn write_i16(&mut self, i: i16) -> crate::Result<()> { |
499 | 202k | self.transport.write_i16::<BigEndian>(i).map_err(From::from) |
500 | 202k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_i16 <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_i16 Line | Count | Source | 498 | 202k | fn write_i16(&mut self, i: i16) -> crate::Result<()> { | 499 | 202k | self.transport.write_i16::<BigEndian>(i).map_err(From::from) | 500 | 202k | } |
|
501 | | |
502 | 137k | fn write_i32(&mut self, i: i32) -> crate::Result<()> { |
503 | 137k | self.transport.write_i32::<BigEndian>(i).map_err(From::from) |
504 | 137k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_i32 <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_i32 Line | Count | Source | 502 | 137k | fn write_i32(&mut self, i: i32) -> crate::Result<()> { | 503 | 137k | self.transport.write_i32::<BigEndian>(i).map_err(From::from) | 504 | 137k | } |
|
505 | | |
506 | 55.7k | fn write_i64(&mut self, i: i64) -> crate::Result<()> { |
507 | 55.7k | self.transport.write_i64::<BigEndian>(i).map_err(From::from) |
508 | 55.7k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_i64 <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_i64 Line | Count | Source | 506 | 55.7k | fn write_i64(&mut self, i: i64) -> crate::Result<()> { | 507 | 55.7k | self.transport.write_i64::<BigEndian>(i).map_err(From::from) | 508 | 55.7k | } |
|
509 | | |
510 | 14.2k | fn write_double(&mut self, d: f64) -> crate::Result<()> { |
511 | 14.2k | self.transport.write_f64::<BigEndian>(d).map_err(From::from) |
512 | 14.2k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_double <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_double Line | Count | Source | 510 | 14.2k | fn write_double(&mut self, d: f64) -> crate::Result<()> { | 511 | 14.2k | self.transport.write_f64::<BigEndian>(d).map_err(From::from) | 512 | 14.2k | } |
|
513 | | |
514 | 35.1k | fn write_string(&mut self, s: &str) -> crate::Result<()> { |
515 | 35.1k | self.write_bytes(s.as_bytes()) |
516 | 35.1k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_string <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_string Line | Count | Source | 514 | 35.1k | fn write_string(&mut self, s: &str) -> crate::Result<()> { | 515 | 35.1k | self.write_bytes(s.as_bytes()) | 516 | 35.1k | } |
|
517 | | |
518 | 13.9k | fn write_uuid(&mut self, uuid: &uuid::Uuid) -> crate::Result<()> { |
519 | 13.9k | self.transport |
520 | 13.9k | .write_all(uuid.as_bytes()) |
521 | 13.9k | .map_err(From::from) |
522 | 13.9k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_uuid <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_uuid Line | Count | Source | 518 | 13.9k | fn write_uuid(&mut self, uuid: &uuid::Uuid) -> crate::Result<()> { | 519 | 13.9k | self.transport | 520 | 13.9k | .write_all(uuid.as_bytes()) | 521 | 13.9k | .map_err(From::from) | 522 | 13.9k | } |
|
523 | | |
524 | 7.38k | fn write_list_begin(&mut self, identifier: &TListIdentifier) -> crate::Result<()> { |
525 | 7.38k | self.write_byte(field_type_to_u8(identifier.element_type))?; |
526 | 7.33k | self.write_i32(identifier.size) |
527 | 7.38k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_list_begin <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_list_begin Line | Count | Source | 524 | 7.38k | fn write_list_begin(&mut self, identifier: &TListIdentifier) -> crate::Result<()> { | 525 | 7.38k | self.write_byte(field_type_to_u8(identifier.element_type))?; | 526 | 7.33k | self.write_i32(identifier.size) | 527 | 7.38k | } |
|
528 | | |
529 | 6.61k | fn write_list_end(&mut self) -> crate::Result<()> { |
530 | 6.61k | Ok(()) |
531 | 6.61k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_list_end <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_list_end Line | Count | Source | 529 | 6.61k | fn write_list_end(&mut self) -> crate::Result<()> { | 530 | 6.61k | Ok(()) | 531 | 6.61k | } |
|
532 | | |
533 | 2.79k | fn write_set_begin(&mut self, identifier: &TSetIdentifier) -> crate::Result<()> { |
534 | 2.79k | self.write_byte(field_type_to_u8(identifier.element_type))?; |
535 | 2.78k | self.write_i32(identifier.size) |
536 | 2.79k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_set_begin <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_set_begin Line | Count | Source | 533 | 2.79k | fn write_set_begin(&mut self, identifier: &TSetIdentifier) -> crate::Result<()> { | 534 | 2.79k | self.write_byte(field_type_to_u8(identifier.element_type))?; | 535 | 2.78k | self.write_i32(identifier.size) | 536 | 2.79k | } |
|
537 | | |
538 | 2.70k | fn write_set_end(&mut self) -> crate::Result<()> { |
539 | 2.70k | Ok(()) |
540 | 2.70k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_set_end <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_set_end Line | Count | Source | 538 | 2.70k | fn write_set_end(&mut self) -> crate::Result<()> { | 539 | 2.70k | Ok(()) | 540 | 2.70k | } |
|
541 | | |
542 | 3.02k | fn write_map_begin(&mut self, identifier: &TMapIdentifier) -> crate::Result<()> { |
543 | 3.02k | let key_type = identifier |
544 | 3.02k | .key_type |
545 | 3.02k | .expect("map identifier to write should contain key type"); |
546 | 3.02k | self.write_byte(field_type_to_u8(key_type))?; |
547 | 3.01k | let val_type = identifier |
548 | 3.01k | .value_type |
549 | 3.01k | .expect("map identifier to write should contain value type"); |
550 | 3.01k | self.write_byte(field_type_to_u8(val_type))?; |
551 | 3.00k | self.write_i32(identifier.size) |
552 | 3.02k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_map_begin <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_map_begin Line | Count | Source | 542 | 3.02k | fn write_map_begin(&mut self, identifier: &TMapIdentifier) -> crate::Result<()> { | 543 | 3.02k | let key_type = identifier | 544 | 3.02k | .key_type | 545 | 3.02k | .expect("map identifier to write should contain key type"); | 546 | 3.02k | self.write_byte(field_type_to_u8(key_type))?; | 547 | 3.01k | let val_type = identifier | 548 | 3.01k | .value_type | 549 | 3.01k | .expect("map identifier to write should contain value type"); | 550 | 3.01k | self.write_byte(field_type_to_u8(val_type))?; | 551 | 3.00k | self.write_i32(identifier.size) | 552 | 3.02k | } |
|
553 | | |
554 | 2.85k | fn write_map_end(&mut self) -> crate::Result<()> { |
555 | 2.85k | Ok(()) |
556 | 2.85k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_map_end <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_map_end Line | Count | Source | 554 | 2.85k | fn write_map_end(&mut self) -> crate::Result<()> { | 555 | 2.85k | Ok(()) | 556 | 2.85k | } |
|
557 | | |
558 | 652 | fn flush(&mut self) -> crate::Result<()> { |
559 | 652 | self.transport.flush().map_err(From::from) |
560 | 652 | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::flush <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::flush Line | Count | Source | 558 | 652 | fn flush(&mut self) -> crate::Result<()> { | 559 | 652 | self.transport.flush().map_err(From::from) | 560 | 652 | } |
|
561 | | |
562 | | // utility |
563 | | // |
564 | | |
565 | 251k | fn write_byte(&mut self, b: u8) -> crate::Result<()> { |
566 | 251k | self.transport.write_u8(b).map_err(From::from) |
567 | 251k | } Unexecuted instantiation: <thrift::protocol::binary::TBinaryOutputProtocol<alloc::boxed::Box<dyn thrift::transport::TWriteTransport + core::marker::Send>> as thrift::protocol::TOutputProtocol>::write_byte <thrift::protocol::binary::TBinaryOutputProtocol<&mut thrift::transport::mem::TBufferChannel> as thrift::protocol::TOutputProtocol>::write_byte Line | Count | Source | 565 | 251k | fn write_byte(&mut self, b: u8) -> crate::Result<()> { | 566 | 251k | self.transport.write_u8(b).map_err(From::from) | 567 | 251k | } |
|
568 | | } |
569 | | |
570 | | /// Factory for creating instances of `TBinaryOutputProtocol`. |
571 | | #[derive(Default)] |
572 | | pub struct TBinaryOutputProtocolFactory; |
573 | | |
574 | | impl TBinaryOutputProtocolFactory { |
575 | | /// Create a `TBinaryOutputProtocolFactory`. |
576 | 0 | pub fn new() -> TBinaryOutputProtocolFactory { |
577 | 0 | TBinaryOutputProtocolFactory {} |
578 | 0 | } |
579 | | } |
580 | | |
581 | | impl TOutputProtocolFactory for TBinaryOutputProtocolFactory { |
582 | 0 | fn create( |
583 | 0 | &self, |
584 | 0 | transport: Box<dyn TWriteTransport + Send>, |
585 | 0 | ) -> Box<dyn TOutputProtocol + Send> { |
586 | 0 | Box::new(TBinaryOutputProtocol::new(transport, true)) |
587 | 0 | } |
588 | | } |
589 | | |
590 | 251k | fn field_type_to_u8(field_type: TType) -> u8 { |
591 | 251k | match field_type { |
592 | 46.7k | TType::Stop => 0x00, |
593 | 0 | TType::Void => 0x01, |
594 | 16.1k | TType::Bool => 0x02, |
595 | 14.3k | TType::I08 => 0x03, // equivalent to TType::Byte |
596 | 14.2k | TType::Double => 0x04, |
597 | 14.3k | TType::I16 => 0x06, |
598 | 53.4k | TType::I32 => 0x08, |
599 | 16.1k | TType::I64 => 0x0A, |
600 | 34.4k | TType::String | TType::Utf7 => 0x0B, |
601 | 14.6k | TType::Struct => 0x0C, |
602 | 3.04k | TType::Map => 0x0D, |
603 | 2.81k | TType::Set => 0x0E, |
604 | 6.95k | TType::List => 0x0F, |
605 | 13.9k | TType::Uuid => 0x10, |
606 | | } |
607 | 251k | } |
608 | | |
609 | 1.16M | fn field_type_from_u8(b: u8) -> crate::Result<TType> { |
610 | 1.16M | match b { |
611 | 487k | 0x00 => Ok(TType::Stop), |
612 | 19.9k | 0x01 => Ok(TType::Void), |
613 | 92.3k | 0x02 => Ok(TType::Bool), |
614 | 47.1k | 0x03 => Ok(TType::I08), // Equivalent to TType::Byte |
615 | 17.7k | 0x04 => Ok(TType::Double), |
616 | 13.8k | 0x06 => Ok(TType::I16), |
617 | 112k | 0x08 => Ok(TType::I32), |
618 | 25.4k | 0x0A => Ok(TType::I64), |
619 | 82.1k | 0x0B => Ok(TType::String), // technically, also a UTF7, but we'll treat it as string |
620 | 166k | 0x0C => Ok(TType::Struct), |
621 | 27.7k | 0x0D => Ok(TType::Map), |
622 | 26.4k | 0x0E => Ok(TType::Set), |
623 | 37.9k | 0x0F => Ok(TType::List), |
624 | 10.5k | 0x10 => Ok(TType::Uuid), |
625 | 471 | unkn => Err(crate::Error::Protocol(ProtocolError { |
626 | 471 | kind: ProtocolErrorKind::InvalidData, |
627 | 471 | message: format!("cannot convert {} to TType", unkn), |
628 | 471 | })), |
629 | | } |
630 | 1.16M | } |
631 | | |
632 | | #[cfg(test)] |
633 | | mod tests { |
634 | | |
635 | | use super::*; |
636 | | use crate::protocol::{ |
637 | | TFieldIdentifier, TInputProtocol, TListIdentifier, TMapIdentifier, TMessageIdentifier, |
638 | | TMessageType, TOutputProtocol, TSetIdentifier, TStructIdentifier, TType, |
639 | | }; |
640 | | use crate::transport::{ReadHalf, TBufferChannel, TIoChannel, WriteHalf}; |
641 | | |
642 | | #[test] |
643 | | fn must_write_strict_message_call_begin() { |
644 | | let (_, mut o_prot) = test_objects(true); |
645 | | |
646 | | let ident = TMessageIdentifier::new("test", TMessageType::Call, 1); |
647 | | assert!(o_prot.write_message_begin(&ident).is_ok()); |
648 | | |
649 | | #[rustfmt::skip] |
650 | | let expected: [u8; 16] = [ |
651 | | 0x80, |
652 | | 0x01, |
653 | | 0x00, |
654 | | 0x01, |
655 | | 0x00, |
656 | | 0x00, |
657 | | 0x00, |
658 | | 0x04, |
659 | | 0x74, |
660 | | 0x65, |
661 | | 0x73, |
662 | | 0x74, |
663 | | 0x00, |
664 | | 0x00, |
665 | | 0x00, |
666 | | 0x01, |
667 | | ]; |
668 | | |
669 | | assert_eq_written_bytes!(o_prot, expected); |
670 | | } |
671 | | |
672 | | #[test] |
673 | | fn must_write_non_strict_message_call_begin() { |
674 | | let (_, mut o_prot) = test_objects(false); |
675 | | |
676 | | let ident = TMessageIdentifier::new("test", TMessageType::Call, 1); |
677 | | assert!(o_prot.write_message_begin(&ident).is_ok()); |
678 | | |
679 | | #[rustfmt::skip] |
680 | | let expected: [u8; 13] = [ |
681 | | 0x00, |
682 | | 0x00, |
683 | | 0x00, |
684 | | 0x04, |
685 | | 0x74, |
686 | | 0x65, |
687 | | 0x73, |
688 | | 0x74, |
689 | | 0x01, |
690 | | 0x00, |
691 | | 0x00, |
692 | | 0x00, |
693 | | 0x01, |
694 | | ]; |
695 | | |
696 | | assert_eq_written_bytes!(o_prot, expected); |
697 | | } |
698 | | |
699 | | #[test] |
700 | | fn must_write_strict_message_reply_begin() { |
701 | | let (_, mut o_prot) = test_objects(true); |
702 | | |
703 | | let ident = TMessageIdentifier::new("test", TMessageType::Reply, 10); |
704 | | assert!(o_prot.write_message_begin(&ident).is_ok()); |
705 | | |
706 | | #[rustfmt::skip] |
707 | | let expected: [u8; 16] = [ |
708 | | 0x80, |
709 | | 0x01, |
710 | | 0x00, |
711 | | 0x02, |
712 | | 0x00, |
713 | | 0x00, |
714 | | 0x00, |
715 | | 0x04, |
716 | | 0x74, |
717 | | 0x65, |
718 | | 0x73, |
719 | | 0x74, |
720 | | 0x00, |
721 | | 0x00, |
722 | | 0x00, |
723 | | 0x0A, |
724 | | ]; |
725 | | |
726 | | assert_eq_written_bytes!(o_prot, expected); |
727 | | } |
728 | | |
729 | | #[test] |
730 | | fn must_write_non_strict_message_reply_begin() { |
731 | | let (_, mut o_prot) = test_objects(false); |
732 | | |
733 | | let ident = TMessageIdentifier::new("test", TMessageType::Reply, 10); |
734 | | assert!(o_prot.write_message_begin(&ident).is_ok()); |
735 | | |
736 | | #[rustfmt::skip] |
737 | | let expected: [u8; 13] = [ |
738 | | 0x00, |
739 | | 0x00, |
740 | | 0x00, |
741 | | 0x04, |
742 | | 0x74, |
743 | | 0x65, |
744 | | 0x73, |
745 | | 0x74, |
746 | | 0x02, |
747 | | 0x00, |
748 | | 0x00, |
749 | | 0x00, |
750 | | 0x0A, |
751 | | ]; |
752 | | |
753 | | assert_eq_written_bytes!(o_prot, expected); |
754 | | } |
755 | | |
756 | | #[test] |
757 | | fn must_round_trip_strict_message_begin() { |
758 | | let (mut i_prot, mut o_prot) = test_objects(true); |
759 | | |
760 | | let sent_ident = TMessageIdentifier::new("test", TMessageType::Call, 1); |
761 | | assert!(o_prot.write_message_begin(&sent_ident).is_ok()); |
762 | | |
763 | | copy_write_buffer_to_read_buffer!(o_prot); |
764 | | |
765 | | let received_ident = assert_success!(i_prot.read_message_begin()); |
766 | | assert_eq!(&received_ident, &sent_ident); |
767 | | } |
768 | | |
769 | | #[test] |
770 | | fn must_round_trip_non_strict_message_begin() { |
771 | | let (mut i_prot, mut o_prot) = test_objects(false); |
772 | | |
773 | | let sent_ident = TMessageIdentifier::new("test", TMessageType::Call, 1); |
774 | | assert!(o_prot.write_message_begin(&sent_ident).is_ok()); |
775 | | |
776 | | copy_write_buffer_to_read_buffer!(o_prot); |
777 | | |
778 | | let received_ident = assert_success!(i_prot.read_message_begin()); |
779 | | assert_eq!(&received_ident, &sent_ident); |
780 | | } |
781 | | |
782 | | #[test] |
783 | | fn must_write_message_end() { |
784 | | assert_no_write(|o| o.write_message_end(), true); |
785 | | } |
786 | | |
787 | | #[test] |
788 | | fn must_write_struct_begin() { |
789 | | assert_no_write( |
790 | | |o| o.write_struct_begin(&TStructIdentifier::new("foo")), |
791 | | true, |
792 | | ); |
793 | | } |
794 | | |
795 | | #[test] |
796 | | fn must_write_struct_end() { |
797 | | // write_struct_end now balances the recursion-depth counter against |
798 | | // write_struct_begin, so pair them (both still emit no bytes). |
799 | | assert_no_write( |
800 | | |o| { |
801 | | o.write_struct_begin(&TStructIdentifier::new("foo"))?; |
802 | | o.write_struct_end() |
803 | | }, |
804 | | true, |
805 | | ); |
806 | | } |
807 | | |
808 | | #[test] |
809 | | fn must_write_field_begin() { |
810 | | let (_, mut o_prot) = test_objects(true); |
811 | | |
812 | | assert!(o_prot |
813 | | .write_field_begin(&TFieldIdentifier::new("some_field", TType::String, 22)) |
814 | | .is_ok()); |
815 | | |
816 | | let expected: [u8; 3] = [0x0B, 0x00, 0x16]; |
817 | | assert_eq_written_bytes!(o_prot, expected); |
818 | | } |
819 | | |
820 | | #[test] |
821 | | fn must_round_trip_field_begin() { |
822 | | let (mut i_prot, mut o_prot) = test_objects(true); |
823 | | |
824 | | let sent_field_ident = TFieldIdentifier::new("foo", TType::I64, 20); |
825 | | assert!(o_prot.write_field_begin(&sent_field_ident).is_ok()); |
826 | | |
827 | | copy_write_buffer_to_read_buffer!(o_prot); |
828 | | |
829 | | let expected_ident = TFieldIdentifier { |
830 | | name: None, |
831 | | field_type: TType::I64, |
832 | | id: Some(20), |
833 | | }; // no name |
834 | | let received_ident = assert_success!(i_prot.read_field_begin()); |
835 | | assert_eq!(&received_ident, &expected_ident); |
836 | | } |
837 | | |
838 | | #[test] |
839 | | fn must_write_stop_field() { |
840 | | let (_, mut o_prot) = test_objects(true); |
841 | | |
842 | | assert!(o_prot.write_field_stop().is_ok()); |
843 | | |
844 | | let expected: [u8; 1] = [0x00]; |
845 | | assert_eq_written_bytes!(o_prot, expected); |
846 | | } |
847 | | |
848 | | #[test] |
849 | | fn must_round_trip_field_stop() { |
850 | | let (mut i_prot, mut o_prot) = test_objects(true); |
851 | | |
852 | | assert!(o_prot.write_field_stop().is_ok()); |
853 | | |
854 | | copy_write_buffer_to_read_buffer!(o_prot); |
855 | | |
856 | | let expected_ident = TFieldIdentifier { |
857 | | name: None, |
858 | | field_type: TType::Stop, |
859 | | id: Some(0), |
860 | | }; // we get id 0 |
861 | | |
862 | | let received_ident = assert_success!(i_prot.read_field_begin()); |
863 | | assert_eq!(&received_ident, &expected_ident); |
864 | | } |
865 | | |
866 | | #[test] |
867 | | fn must_write_field_end() { |
868 | | assert_no_write(|o| o.write_field_end(), true); |
869 | | } |
870 | | |
871 | | #[test] |
872 | | fn must_write_list_begin() { |
873 | | let (_, mut o_prot) = test_objects(true); |
874 | | |
875 | | assert!(o_prot |
876 | | .write_list_begin(&TListIdentifier::new(TType::Bool, 5)) |
877 | | .is_ok()); |
878 | | |
879 | | let expected: [u8; 5] = [0x02, 0x00, 0x00, 0x00, 0x05]; |
880 | | assert_eq_written_bytes!(o_prot, expected); |
881 | | } |
882 | | |
883 | | #[test] |
884 | | fn must_round_trip_list_begin() { |
885 | | let (mut i_prot, mut o_prot) = test_objects(true); |
886 | | |
887 | | let ident = TListIdentifier::new(TType::I32, 4); |
888 | | assert!(o_prot.write_list_begin(&ident).is_ok()); |
889 | | assert!(o_prot.write_i32(10).is_ok()); |
890 | | assert!(o_prot.write_i32(20).is_ok()); |
891 | | assert!(o_prot.write_i32(30).is_ok()); |
892 | | assert!(o_prot.write_i32(40).is_ok()); |
893 | | |
894 | | assert!(o_prot.write_list_end().is_ok()); |
895 | | |
896 | | copy_write_buffer_to_read_buffer!(o_prot); |
897 | | |
898 | | let received_ident = assert_success!(i_prot.read_list_begin()); |
899 | | assert_eq!(&received_ident, &ident); |
900 | | |
901 | | assert_eq!(i_prot.read_i32().unwrap(), 10); |
902 | | assert_eq!(i_prot.read_i32().unwrap(), 20); |
903 | | assert_eq!(i_prot.read_i32().unwrap(), 30); |
904 | | assert_eq!(i_prot.read_i32().unwrap(), 40); |
905 | | |
906 | | assert!(i_prot.read_list_end().is_ok()); |
907 | | } |
908 | | |
909 | | #[test] |
910 | | fn must_write_list_end() { |
911 | | assert_no_write(|o| o.write_list_end(), true); |
912 | | } |
913 | | |
914 | | #[test] |
915 | | fn must_write_set_begin() { |
916 | | let (_, mut o_prot) = test_objects(true); |
917 | | |
918 | | assert!(o_prot |
919 | | .write_set_begin(&TSetIdentifier::new(TType::I16, 7)) |
920 | | .is_ok()); |
921 | | |
922 | | let expected: [u8; 5] = [0x06, 0x00, 0x00, 0x00, 0x07]; |
923 | | assert_eq_written_bytes!(o_prot, expected); |
924 | | } |
925 | | |
926 | | #[test] |
927 | | fn must_round_trip_set_begin() { |
928 | | let (mut i_prot, mut o_prot) = test_objects(true); |
929 | | |
930 | | let ident = TSetIdentifier::new(TType::I64, 3); |
931 | | assert!(o_prot.write_set_begin(&ident).is_ok()); |
932 | | assert!(o_prot.write_i64(123).is_ok()); |
933 | | assert!(o_prot.write_i64(456).is_ok()); |
934 | | assert!(o_prot.write_i64(789).is_ok()); |
935 | | |
936 | | assert!(o_prot.write_set_end().is_ok()); |
937 | | |
938 | | copy_write_buffer_to_read_buffer!(o_prot); |
939 | | |
940 | | let received_ident_result = i_prot.read_set_begin(); |
941 | | assert!(received_ident_result.is_ok()); |
942 | | assert_eq!(&received_ident_result.unwrap(), &ident); |
943 | | |
944 | | assert_eq!(i_prot.read_i64().unwrap(), 123); |
945 | | assert_eq!(i_prot.read_i64().unwrap(), 456); |
946 | | assert_eq!(i_prot.read_i64().unwrap(), 789); |
947 | | |
948 | | assert!(i_prot.read_set_end().is_ok()); |
949 | | } |
950 | | |
951 | | #[test] |
952 | | fn must_write_set_end() { |
953 | | assert_no_write(|o| o.write_set_end(), true); |
954 | | } |
955 | | |
956 | | #[test] |
957 | | fn must_write_map_begin() { |
958 | | let (_, mut o_prot) = test_objects(true); |
959 | | |
960 | | assert!(o_prot |
961 | | .write_map_begin(&TMapIdentifier::new(TType::I64, TType::Struct, 32)) |
962 | | .is_ok()); |
963 | | |
964 | | let expected: [u8; 6] = [0x0A, 0x0C, 0x00, 0x00, 0x00, 0x20]; |
965 | | assert_eq_written_bytes!(o_prot, expected); |
966 | | } |
967 | | |
968 | | #[test] |
969 | | fn must_round_trip_map_begin() { |
970 | | let (mut i_prot, mut o_prot) = test_objects(true); |
971 | | |
972 | | let ident = TMapIdentifier::new(TType::String, TType::I32, 2); |
973 | | assert!(o_prot.write_map_begin(&ident).is_ok()); |
974 | | assert!(o_prot.write_string("key1").is_ok()); |
975 | | assert!(o_prot.write_i32(100).is_ok()); |
976 | | assert!(o_prot.write_string("key2").is_ok()); |
977 | | assert!(o_prot.write_i32(200).is_ok()); |
978 | | |
979 | | assert!(o_prot.write_map_end().is_ok()); |
980 | | |
981 | | copy_write_buffer_to_read_buffer!(o_prot); |
982 | | |
983 | | let received_ident = assert_success!(i_prot.read_map_begin()); |
984 | | assert_eq!(&received_ident, &ident); |
985 | | |
986 | | assert_eq!(i_prot.read_string().unwrap(), "key1"); |
987 | | assert_eq!(i_prot.read_i32().unwrap(), 100); |
988 | | assert_eq!(i_prot.read_string().unwrap(), "key2"); |
989 | | assert_eq!(i_prot.read_i32().unwrap(), 200); |
990 | | |
991 | | assert!(i_prot.read_map_end().is_ok()); |
992 | | } |
993 | | |
994 | | #[test] |
995 | | fn must_write_map_end() { |
996 | | assert_no_write(|o| o.write_map_end(), true); |
997 | | } |
998 | | |
999 | | #[test] |
1000 | | fn must_write_bool_true() { |
1001 | | let (_, mut o_prot) = test_objects(true); |
1002 | | |
1003 | | assert!(o_prot.write_bool(true).is_ok()); |
1004 | | |
1005 | | let expected: [u8; 1] = [0x01]; |
1006 | | assert_eq_written_bytes!(o_prot, expected); |
1007 | | } |
1008 | | |
1009 | | #[test] |
1010 | | fn must_write_bool_false() { |
1011 | | let (_, mut o_prot) = test_objects(true); |
1012 | | |
1013 | | assert!(o_prot.write_bool(false).is_ok()); |
1014 | | |
1015 | | let expected: [u8; 1] = [0x00]; |
1016 | | assert_eq_written_bytes!(o_prot, expected); |
1017 | | } |
1018 | | |
1019 | | #[test] |
1020 | | fn must_read_bool_true() { |
1021 | | let (mut i_prot, _) = test_objects(true); |
1022 | | |
1023 | | set_readable_bytes!(i_prot, &[0x01]); |
1024 | | |
1025 | | let read_bool = assert_success!(i_prot.read_bool()); |
1026 | | assert!(read_bool); |
1027 | | } |
1028 | | |
1029 | | #[test] |
1030 | | fn must_read_bool_false() { |
1031 | | let (mut i_prot, _) = test_objects(true); |
1032 | | |
1033 | | set_readable_bytes!(i_prot, &[0x00]); |
1034 | | |
1035 | | let read_bool = assert_success!(i_prot.read_bool()); |
1036 | | assert!(!read_bool); |
1037 | | } |
1038 | | |
1039 | | #[test] |
1040 | | fn must_allow_any_non_zero_value_to_be_interpreted_as_bool_true() { |
1041 | | let (mut i_prot, _) = test_objects(true); |
1042 | | |
1043 | | set_readable_bytes!(i_prot, &[0xAC]); |
1044 | | |
1045 | | let read_bool = assert_success!(i_prot.read_bool()); |
1046 | | assert!(read_bool); |
1047 | | } |
1048 | | |
1049 | | #[test] |
1050 | | fn must_write_bytes() { |
1051 | | let (_, mut o_prot) = test_objects(true); |
1052 | | |
1053 | | let bytes: [u8; 10] = [0x0A, 0xCC, 0xD1, 0x84, 0x99, 0x12, 0xAB, 0xBB, 0x45, 0xDF]; |
1054 | | |
1055 | | assert!(o_prot.write_bytes(&bytes).is_ok()); |
1056 | | |
1057 | | let buf = o_prot.transport.write_bytes(); |
1058 | | assert_eq!(&buf[0..4], [0x00, 0x00, 0x00, 0x0A]); // length |
1059 | | assert_eq!(&buf[4..], bytes); // actual bytes |
1060 | | } |
1061 | | |
1062 | | #[test] |
1063 | | fn must_write_uuid() { |
1064 | | let (_, mut o_prot) = test_objects(true); |
1065 | | let uuid = uuid::Uuid::new_v4(); |
1066 | | assert!(o_prot.write_uuid(&uuid).is_ok()); |
1067 | | let buf = o_prot.transport.write_bytes(); |
1068 | | assert_eq!(&buf, uuid.as_bytes()); |
1069 | | } |
1070 | | |
1071 | | #[test] |
1072 | | fn must_round_trip_uuid() { |
1073 | | let (mut i_prot, mut o_prot) = test_objects(true); |
1074 | | let uuid = uuid::uuid!("F9168C5E-CEB2-4faa-B6BF-329BF39FA1E4"); |
1075 | | assert!(o_prot.write_uuid(&uuid).is_ok()); |
1076 | | copy_write_buffer_to_read_buffer!(o_prot); |
1077 | | let received_uuid = assert_success!(i_prot.read_uuid()); |
1078 | | assert_eq!(&received_uuid, &uuid); |
1079 | | } |
1080 | | |
1081 | | #[test] |
1082 | | fn must_round_trip_bytes() { |
1083 | | let (mut i_prot, mut o_prot) = test_objects(true); |
1084 | | |
1085 | | #[rustfmt::skip] |
1086 | | let bytes: [u8; 25] = [ |
1087 | | 0x20, |
1088 | | 0xFD, |
1089 | | 0x18, |
1090 | | 0x84, |
1091 | | 0x99, |
1092 | | 0x12, |
1093 | | 0xAB, |
1094 | | 0xBB, |
1095 | | 0x45, |
1096 | | 0xDF, |
1097 | | 0x34, |
1098 | | 0xDC, |
1099 | | 0x98, |
1100 | | 0xA4, |
1101 | | 0x6D, |
1102 | | 0xF3, |
1103 | | 0x99, |
1104 | | 0xB4, |
1105 | | 0xB7, |
1106 | | 0xD4, |
1107 | | 0x9C, |
1108 | | 0xA5, |
1109 | | 0xB3, |
1110 | | 0xC9, |
1111 | | 0x88, |
1112 | | ]; |
1113 | | |
1114 | | assert!(o_prot.write_bytes(&bytes).is_ok()); |
1115 | | |
1116 | | copy_write_buffer_to_read_buffer!(o_prot); |
1117 | | |
1118 | | let received_bytes = assert_success!(i_prot.read_bytes()); |
1119 | | assert_eq!(&received_bytes, &bytes); |
1120 | | } |
1121 | | |
1122 | | fn test_objects( |
1123 | | strict: bool, |
1124 | | ) -> ( |
1125 | | TBinaryInputProtocol<ReadHalf<TBufferChannel>>, |
1126 | | TBinaryOutputProtocol<WriteHalf<TBufferChannel>>, |
1127 | | ) { |
1128 | | let mem = TBufferChannel::with_capacity(200, 200); |
1129 | | |
1130 | | let (r_mem, w_mem) = mem.split().unwrap(); |
1131 | | |
1132 | | let i_prot = TBinaryInputProtocol::new(r_mem, strict); |
1133 | | let o_prot = TBinaryOutputProtocol::new(w_mem, strict); |
1134 | | |
1135 | | (i_prot, o_prot) |
1136 | | } |
1137 | | |
1138 | | fn assert_no_write<F>(mut write_fn: F, strict: bool) |
1139 | | where |
1140 | | F: FnMut(&mut TBinaryOutputProtocol<WriteHalf<TBufferChannel>>) -> crate::Result<()>, |
1141 | | { |
1142 | | let (_, mut o_prot) = test_objects(strict); |
1143 | | assert!(write_fn(&mut o_prot).is_ok()); |
1144 | | assert_eq!(o_prot.transport.write_bytes().len(), 0); |
1145 | | } |
1146 | | |
1147 | | #[test] |
1148 | | fn must_enforce_recursion_depth_limit() { |
1149 | | let mem = TBufferChannel::with_capacity(40, 40); |
1150 | | let (r_mem, _) = mem.split().unwrap(); |
1151 | | |
1152 | | let config = TConfiguration::builder() |
1153 | | .max_recursion_depth(Some(2)) |
1154 | | .build() |
1155 | | .unwrap(); |
1156 | | let mut i_prot = TBinaryInputProtocol::with_config(r_mem, true, config); |
1157 | | |
1158 | | assert!(i_prot.read_struct_begin().is_ok()); |
1159 | | assert_eq!(i_prot.recursion_depth, 1); |
1160 | | |
1161 | | assert!(i_prot.read_struct_begin().is_ok()); |
1162 | | assert_eq!(i_prot.recursion_depth, 2); |
1163 | | |
1164 | | let result = i_prot.read_struct_begin(); |
1165 | | assert!(result.is_err()); |
1166 | | match result { |
1167 | | Err(crate::Error::Protocol(e)) => { |
1168 | | assert_eq!(e.kind, ProtocolErrorKind::DepthLimit); |
1169 | | } |
1170 | | _ => panic!("Expected protocol error with DepthLimit"), |
1171 | | } |
1172 | | |
1173 | | assert!(i_prot.read_struct_end().is_ok()); |
1174 | | assert_eq!(i_prot.recursion_depth, 1); |
1175 | | assert!(i_prot.read_struct_end().is_ok()); |
1176 | | assert_eq!(i_prot.recursion_depth, 0); |
1177 | | } |
1178 | | |
1179 | | #[test] |
1180 | | fn must_reject_negative_container_sizes() { |
1181 | | let mem = TBufferChannel::with_capacity(40, 40); |
1182 | | let (r_mem, mut w_mem) = mem.split().unwrap(); |
1183 | | |
1184 | | let mut i_prot = TBinaryInputProtocol::new(r_mem, true); |
1185 | | |
1186 | | w_mem.set_readable_bytes(&[0x0F, 0xFF, 0xFF, 0xFF, 0xFF]); |
1187 | | |
1188 | | let result = i_prot.read_list_begin(); |
1189 | | assert!(result.is_err()); |
1190 | | match result { |
1191 | | Err(crate::Error::Protocol(e)) => { |
1192 | | assert_eq!(e.kind, ProtocolErrorKind::NegativeSize); |
1193 | | } |
1194 | | _ => panic!("Expected protocol error with NegativeSize"), |
1195 | | } |
1196 | | } |
1197 | | |
1198 | | #[test] |
1199 | | fn must_enforce_container_size_limit() { |
1200 | | let mem = TBufferChannel::with_capacity(40, 40); |
1201 | | let (r_mem, mut w_mem) = mem.split().unwrap(); |
1202 | | |
1203 | | let config = TConfiguration::builder() |
1204 | | .max_container_size(Some(100)) |
1205 | | .build() |
1206 | | .unwrap(); |
1207 | | |
1208 | | let mut i_prot = TBinaryInputProtocol::with_config(r_mem, true, config); |
1209 | | |
1210 | | w_mem.set_readable_bytes(&[0x0F, 0x00, 0x00, 0x00, 0xC8]); |
1211 | | |
1212 | | let result = i_prot.read_list_begin(); |
1213 | | assert!(result.is_err()); |
1214 | | match result { |
1215 | | Err(crate::Error::Protocol(e)) => { |
1216 | | assert_eq!(e.kind, ProtocolErrorKind::SizeLimit); |
1217 | | assert!(e |
1218 | | .message |
1219 | | .contains("Container size 200 exceeds maximum allowed size of 100")); |
1220 | | } |
1221 | | _ => panic!("Expected protocol error with SizeLimit"), |
1222 | | } |
1223 | | } |
1224 | | |
1225 | | #[test] |
1226 | | fn must_allow_containers_within_limit() { |
1227 | | let mem = TBufferChannel::with_capacity(200, 200); |
1228 | | let (r_mem, mut w_mem) = mem.split().unwrap(); |
1229 | | |
1230 | | // Create protocol with container limit of 100 |
1231 | | let config = TConfiguration::builder() |
1232 | | .max_container_size(Some(100)) |
1233 | | .build() |
1234 | | .unwrap(); |
1235 | | let mut i_prot = TBinaryInputProtocol::with_config(r_mem, true, config); |
1236 | | |
1237 | | let mut data = vec![0x08]; // TType::I32 |
1238 | | data.extend_from_slice(&5i32.to_be_bytes()); // size = 5 |
1239 | | |
1240 | | for i in 1i32..=5i32 { |
1241 | | data.extend_from_slice(&(i * 10).to_be_bytes()); |
1242 | | } |
1243 | | |
1244 | | w_mem.set_readable_bytes(&data); |
1245 | | |
1246 | | let result = i_prot.read_list_begin(); |
1247 | | assert!(result.is_ok()); |
1248 | | let list_ident = result.unwrap(); |
1249 | | assert_eq!(list_ident.size, 5); |
1250 | | assert_eq!(list_ident.element_type, TType::I32); |
1251 | | } |
1252 | | |
1253 | | #[test] |
1254 | | fn must_enforce_string_size_limit() { |
1255 | | let mem = TBufferChannel::with_capacity(100, 100); |
1256 | | let (r_mem, mut w_mem) = mem.split().unwrap(); |
1257 | | |
1258 | | let config = TConfiguration::builder() |
1259 | | .max_string_size(Some(1000)) |
1260 | | .build() |
1261 | | .unwrap(); |
1262 | | let mut i_prot = TBinaryInputProtocol::with_config(r_mem, true, config); |
1263 | | |
1264 | | w_mem.set_readable_bytes(&[0x00, 0x00, 0x07, 0xD0]); |
1265 | | |
1266 | | let result = i_prot.read_string(); |
1267 | | assert!(result.is_err()); |
1268 | | match result { |
1269 | | Err(crate::Error::Protocol(e)) => { |
1270 | | assert_eq!(e.kind, ProtocolErrorKind::SizeLimit); |
1271 | | assert!(e |
1272 | | .message |
1273 | | .contains("Byte array size 2000 exceeds maximum allowed size of 1000")); |
1274 | | } |
1275 | | _ => panic!("Expected protocol error with SizeLimit"), |
1276 | | } |
1277 | | } |
1278 | | |
1279 | | #[test] |
1280 | | fn must_enforce_string_size_limit_on_non_strict_message_name() { |
1281 | | let mem = TBufferChannel::with_capacity(100, 100); |
1282 | | let (r_mem, mut w_mem) = mem.split().unwrap(); |
1283 | | |
1284 | | let config = TConfiguration::builder() |
1285 | | .max_string_size(Some(1000)) |
1286 | | .build() |
1287 | | .unwrap(); |
1288 | | // non-strict: the first 4 bytes are the (positive) message-name length |
1289 | | let mut i_prot = TBinaryInputProtocol::with_config(r_mem, false, config); |
1290 | | |
1291 | | w_mem.set_readable_bytes(&[0x00, 0x00, 0x07, 0xD0]); |
1292 | | |
1293 | | let result = i_prot.read_message_begin(); |
1294 | | assert!(result.is_err()); |
1295 | | match result { |
1296 | | Err(crate::Error::Protocol(e)) => { |
1297 | | assert_eq!(e.kind, ProtocolErrorKind::SizeLimit); |
1298 | | assert!(e |
1299 | | .message |
1300 | | .contains("Message name size 2000 exceeds maximum allowed size of 1000")); |
1301 | | } |
1302 | | _ => panic!("Expected protocol error with SizeLimit"), |
1303 | | } |
1304 | | } |
1305 | | |
1306 | | #[test] |
1307 | | fn must_allow_non_strict_message_name_at_limit() { |
1308 | | let mem = TBufferChannel::with_capacity(100, 100); |
1309 | | let (r_mem, mut w_mem) = mem.split().unwrap(); |
1310 | | |
1311 | | let config = TConfiguration::builder() |
1312 | | .max_string_size(Some(5)) |
1313 | | .build() |
1314 | | .unwrap(); |
1315 | | // non-strict: the first 4 bytes are the (positive) message-name length |
1316 | | let mut i_prot = TBinaryInputProtocol::with_config(r_mem, false, config); |
1317 | | |
1318 | | // name length 5 (== limit), name "hello", message type Call, sequence 0 |
1319 | | w_mem.set_readable_bytes(&[ |
1320 | | 0x00, 0x00, 0x00, 0x05, b'h', b'e', b'l', b'l', b'o', 0x01, 0x00, 0x00, 0x00, 0x00, |
1321 | | ]); |
1322 | | |
1323 | | let ident = i_prot.read_message_begin().unwrap(); |
1324 | | assert_eq!(ident.name, "hello"); |
1325 | | assert_eq!(ident.message_type, TMessageType::Call); |
1326 | | assert_eq!(ident.sequence_number, 0); |
1327 | | } |
1328 | | |
1329 | | #[test] |
1330 | | fn must_allow_strings_within_limit() { |
1331 | | let mem = TBufferChannel::with_capacity(100, 100); |
1332 | | let (r_mem, mut w_mem) = mem.split().unwrap(); |
1333 | | |
1334 | | let config = TConfiguration::builder() |
1335 | | .max_string_size(Some(1000)) |
1336 | | .build() |
1337 | | .unwrap(); |
1338 | | let mut i_prot = TBinaryInputProtocol::with_config(r_mem, true, config); |
1339 | | |
1340 | | w_mem.set_readable_bytes(&[0x00, 0x00, 0x00, 0x05, b'h', b'e', b'l', b'l', b'o']); |
1341 | | |
1342 | | let result = i_prot.read_string(); |
1343 | | assert!(result.is_ok()); |
1344 | | assert_eq!(result.unwrap(), "hello"); |
1345 | | } |
1346 | | } |