1 /** @file
2  *  @brief Internal APIs for Bluetooth SCO handling.
3  */
4 /*
5  * Copyright 2024 NXP
6  *
7  * SPDX-License-Identifier: Apache-2.0
8  */
9 
10 /** @brief Life-span states of SCO channel. Used only by internal APIs
11  *  dealing with setting channel to proper state depending on operational
12  *  context.
13  */
14 enum bt_sco_state {
15 	/** Channel disconnected */
16 	BT_SCO_STATE_DISCONNECTED,
17 	/** Channel is pending ACL encryption before connecting */
18 	BT_SCO_STATE_ENCRYPT_PENDING,
19 	/** Channel in connecting state */
20 	BT_SCO_STATE_CONNECTING,
21 	/** Channel ready for upper layer traffic on it */
22 	BT_SCO_STATE_CONNECTED,
23 	/** Channel in disconnecting state */
24 	BT_SCO_STATE_DISCONNECTING,
25 };
26 
27 struct bt_sco_chan;
28 struct bt_sco_chan_ops {
29 	/** @brief Channel connected callback
30 	 *
31 	 *  If this callback is provided it will be called whenever the
32 	 *  connection completes.
33 	 *
34 	 *  @param chan The channel that has been connected
35 	 */
36 	void (*connected)(struct bt_sco_chan *chan);
37 
38 	/** @brief Channel disconnected callback
39 	 *
40 	 *  If this callback is provided it will be called whenever the
41 	 *  channel is disconnected, including when a connection gets
42 	 *  rejected or when setting security fails.
43 	 *
44 	 *  @param chan   The channel that has been Disconnected
45 	 *  @param reason BT_HCI_ERR_* reason for the disconnection.
46 	 */
47 	void (*disconnected)(struct bt_sco_chan *chan, uint8_t reason);
48 };
49 
50 struct bt_sco_chan {
51 	struct bt_conn *sco;
52 	/** Channel operations reference */
53 	struct bt_sco_chan_ops		*ops;
54 
55 	enum bt_sco_state		state;
56 };
57 
58 /** @brief Initiate an SCO connection to a remote device.
59  *
60  *  Allows initiate new SCO link to remote peer using its address.
61  *
62  *  The caller gets a new reference to the connection object which must be
63  *  released with bt_conn_unref() once done using the object.
64  *
65  *  @param peer  Remote address.
66  *  @param chan  sco chan object.
67  *
68  *  @return Valid connection object on success or NULL otherwise.
69  */
70 struct bt_conn *bt_conn_create_sco(const bt_addr_t *peer, struct bt_sco_chan *chan);
71 
72 /** @brief SCO Accept Info Structure */
73 struct bt_sco_accept_info {
74 	/** The ACL connection that is requesting authorization */
75 	struct bt_conn *acl;
76 
77 	/** class code of peer device */
78 	uint8_t   dev_class[3];
79 
80 	/** link type */
81 	uint8_t   link_type;
82 };
83 
84 /** @brief SCO Server structure. */
85 struct bt_sco_server {
86 	/** Required minimum security level.
87 	 * Only available when @kconfig{CONFIG_BT_SMP} is enabled.
88 	 */
89 	bt_security_t		sec_level;
90 	/** @brief Server accept callback
91 	 *
92 	 *  This callback is called whenever a new incoming connection requires
93 	 *  authorization.
94 	 *
95 	 *  @param info The SCO accept information structure
96 	 *  @param chan Pointer to receive the allocated channel
97 	 *
98 	 *  @return 0 in case of success or negative value in case of error.
99 	 */
100 	int (*accept)(const struct bt_sco_accept_info *info,
101 			  struct bt_sco_chan **chan);
102 };
103 
104 /** @brief Register SCO server.
105  *
106  *  Register SCO server, each new connection is authorized using the accept()
107  *  callback which in case of success shall allocate the channel structure
108  *  to be used by the new connection.
109  *
110  *  @param server Server structure.
111  *
112  *  @return 0 in case of success or negative value in case of error.
113  */
114 int bt_sco_server_register(struct bt_sco_server *server);
115 
116 /** @brief Unregister SCO server.
117  *
118  *  Unregister previously registered SCO server.
119  *
120  *  @param server Server structure.
121  *
122  *  @return 0 in case of success or negative value in case of error.
123  */
124 int bt_sco_server_unregister(struct bt_sco_server *server);
125 
126 /** @brief sco channel connected.
127  *
128  *  sco channel connected
129  *
130  *  @param sco SCO connection object.
131  */
132 void bt_sco_connected(struct bt_conn *sco);
133 
134 /** @brief sco channel disconnected.
135  *
136  *  sco channel disconnected
137  *
138  *  @param sco SCO connection object.
139  */
140 void bt_sco_disconnected(struct bt_conn *sco);
141 
142 uint8_t bt_esco_conn_req(struct bt_hci_evt_conn_request *evt);
143 
144 #if defined(CONFIG_BT_CONN_LOG_LEVEL_DBG)
145 void bt_sco_chan_set_state_debug(struct bt_sco_chan *chan,
146 				 enum bt_sco_state state,
147 				 const char *func, int line);
148 #define bt_sco_chan_set_state(_chan, _state) \
149 	bt_sco_chan_set_state_debug(_chan, _state, __func__, __LINE__)
150 #else
151 void bt_sco_chan_set_state(struct bt_sco_chan *chan, enum bt_sco_state state);
152 #endif /* CONFIG_BT_CONN_LOG_LEVEL_DBG */
153