Merge "floss: Socket: Fix CONNECT_COMPLETE_SIZE and revise unittest" into main
diff --git a/system/gd/rust/topshim/src/profiles/socket.rs b/system/gd/rust/topshim/src/profiles/socket.rs
index eddbd0d..7631510 100644
--- a/system/gd/rust/topshim/src/profiles/socket.rs
+++ b/system/gd/rust/topshim/src/profiles/socket.rs
@@ -64,9 +64,8 @@
pub max_rx_packet_size: u16,
}
-/// Size of connect complete data. The data read from libbluetooth is packed but
-/// the Rust struct is not, so depend on this value for validation.
-pub const CONNECT_COMPLETE_SIZE: usize = 20;
+/// Size of connect complete data. This is the packed data length from libbluetooth.
+pub const CONNECT_COMPLETE_SIZE: usize = std::mem::size_of::<bindings::sock_connect_signal_t>();
// Convert from raw bytes to struct.
impl TryFrom<&[u8]> for ConnectionComplete {
@@ -261,37 +260,48 @@
#[test]
fn test_conncomplete_parsing() {
// Actual slice size doesn't match
- let small_input = [0u8; 18];
- let large_input = [0u8; 21];
+ let small_input = [0u8; CONNECT_COMPLETE_SIZE - 1];
+ let large_input = [0u8; CONNECT_COMPLETE_SIZE + 1];
assert_eq!(false, ConnectionComplete::try_from(&small_input[0..]).is_ok());
assert_eq!(false, ConnectionComplete::try_from(&large_input[0..]).is_ok());
// Size param in slice doesn't match.
- let mut size_no_match = vec![0x0u8, 0x13u8];
- size_no_match.extend([0u8; 18]);
+ let mut size_no_match: Vec<u8> = vec![];
+ size_no_match.extend(i16::to_ne_bytes((CONNECT_COMPLETE_SIZE - 1) as i16));
+ size_no_match.extend([0u8; CONNECT_COMPLETE_SIZE - 2]);
assert_eq!(false, ConnectionComplete::try_from(size_no_match.as_slice()).is_ok());
- // Valid input with various values.
- let raw_addr = RawAddress { address: [0x1, 0x2, 0x3, 0x4, 0x5, 0x6] };
- let mut valid: Vec<u8> = vec![];
- valid.extend(u16::to_ne_bytes(20));
- valid.extend(raw_addr.to_byte_arr());
- valid.extend(i32::to_ne_bytes(1));
- valid.extend(i32::to_ne_bytes(5));
- valid.extend(u16::to_ne_bytes(16));
- valid.extend(u16::to_ne_bytes(17));
+ let valid_signal = bindings::sock_connect_signal_t {
+ size: CONNECT_COMPLETE_SIZE as i16,
+ bd_addr: RawAddress { address: [0x1, 0x2, 0x3, 0x4, 0x5, 0x6] },
+ channel: 1_i32,
+ status: 5_i32,
+ max_tx_packet_size: 16_u16,
+ max_rx_packet_size: 17_u16,
+ conn_uuid_lsb: 0x0000113500001135_u64,
+ conn_uuid_msb: 0x1135000011350000_u64,
+ };
+ // SAFETY: The sock_connect_signal_t type has size CONNECT_COMPLETE_SIZE,
+ // and has no padding, so it's safe to convert it to a byte array.
+ let valid_raw_data: &[u8] = unsafe {
+ std::slice::from_raw_parts(
+ (&valid_signal as *const bindings::sock_connect_signal_t) as *const u8,
+ CONNECT_COMPLETE_SIZE,
+ )
+ };
- let result = ConnectionComplete::try_from(valid.as_slice());
+ let result = ConnectionComplete::try_from(valid_raw_data);
assert_eq!(true, result.is_ok());
if let Ok(cc) = result {
- assert_eq!(cc.size, 20u16);
- assert_eq!(cc.channel, 1);
- assert_eq!(cc.status, 5);
- assert_eq!(cc.max_tx_packet_size, 16u16);
- assert_eq!(cc.max_rx_packet_size, 17u16);
+ assert_eq!(cc.size, CONNECT_COMPLETE_SIZE as u16);
+ assert_eq!(cc.addr, RawAddress { address: [0x1, 0x2, 0x3, 0x4, 0x5, 0x6] });
+ assert_eq!(cc.channel, 1_i32);
+ assert_eq!(cc.status, 5_i32);
+ assert_eq!(cc.max_tx_packet_size, 16_u16);
+ assert_eq!(cc.max_rx_packet_size, 17_u16);
}
}
}