bt_rfcomm/
lib.rs

1// Copyright 2021 The Fuchsia Authors. All rights reserved.
2// Use of this source code is governed by a BSD-style license that can be
3// found in the LICENSE file.
4
5/// The direct link connection identifier (DLCI) definitions.
6mod dlci;
7pub use dlci::{ServerChannel, DLCI};
8
9/// The error type used throughout this library.
10mod error;
11pub use error::Error as RfcommError;
12
13/// The definitions for RFCOMM frames - the basic unit of data in RFCOMM.
14pub mod frame;
15
16/// Convenience helpers for the `bredr.Profile` API RFCOMM operations.
17pub mod profile;
18
19/// The Role assigned to a device in an RFCOMM Session.
20#[derive(Copy, Clone, Debug, PartialEq)]
21pub enum Role {
22    /// RFCOMM Session has not started up the start-up procedure.
23    Unassigned,
24    /// The start-up procedure is in progress, and so the role is being negotiated.
25    Negotiating,
26    /// The device that starts up the multiplexer control channel is considered
27    /// the initiator.
28    Initiator,
29    /// The device that responds to the start-up procedure.
30    Responder,
31}
32
33impl Role {
34    /// Returns the Role opposite to the current Role.
35    pub fn opposite_role(&self) -> Self {
36        match self {
37            Role::Initiator => Role::Responder,
38            Role::Responder => Role::Initiator,
39            role => *role,
40        }
41    }
42
43    /// Returns true if the multiplexer has started - namely, a role has been assigned.
44    pub fn is_multiplexer_started(&self) -> bool {
45        *self == Role::Initiator || *self == Role::Responder
46    }
47}
48
49/// Returns the maximum RFCOMM packet size that can be used for the provided L2CAP `mtu`.
50/// It is assumed that `mtu` is a valid L2CAP MTU.
51pub fn max_packet_size_from_l2cap_mtu(mtu: u16) -> u16 {
52    mtu - crate::frame::MAX_RFCOMM_HEADER_SIZE as u16
53}
54
55#[cfg(test)]
56mod tests {
57    use super::*;
58
59    #[test]
60    fn test_convert_to_opposite_role() {
61        let role = Role::Initiator;
62        assert_eq!(role.opposite_role(), Role::Responder);
63
64        let role = Role::Responder;
65        assert_eq!(role.opposite_role(), Role::Initiator);
66
67        let role = Role::Unassigned;
68        assert_eq!(role.opposite_role(), Role::Unassigned);
69
70        let role = Role::Negotiating;
71        assert_eq!(role.opposite_role(), Role::Negotiating);
72    }
73}