|
@@ -455,7 +455,7 @@ void l2cap_chan_set_defaults(struct l2cap_chan *chan)
|
|
|
set_bit(FLAG_FORCE_ACTIVE, &chan->flags);
|
|
|
}
|
|
|
|
|
|
-static void __l2cap_chan_add(struct l2cap_conn *conn, struct l2cap_chan *chan)
|
|
|
+void __l2cap_chan_add(struct l2cap_conn *conn, struct l2cap_chan *chan)
|
|
|
{
|
|
|
BT_DBG("conn %p, psm 0x%2.2x, dcid 0x%4.4x", conn,
|
|
|
__le16_to_cpu(chan->psm), chan->dcid);
|
|
@@ -946,6 +946,18 @@ static inline int __l2cap_no_conn_pending(struct l2cap_chan *chan)
|
|
|
return !test_bit(CONF_CONNECT_PEND, &chan->conf_state);
|
|
|
}
|
|
|
|
|
|
+static bool __amp_capable(struct l2cap_chan *chan)
|
|
|
+{
|
|
|
+ struct l2cap_conn *conn = chan->conn;
|
|
|
+
|
|
|
+ if (enable_hs &&
|
|
|
+ chan->chan_policy == BT_CHANNEL_POLICY_AMP_PREFERRED &&
|
|
|
+ conn->fixed_chan_mask & L2CAP_FC_A2MP)
|
|
|
+ return true;
|
|
|
+ else
|
|
|
+ return false;
|
|
|
+}
|
|
|
+
|
|
|
static void l2cap_send_conn_req(struct l2cap_chan *chan)
|
|
|
{
|
|
|
struct l2cap_conn *conn = chan->conn;
|
|
@@ -972,6 +984,16 @@ static void l2cap_chan_ready(struct l2cap_chan *chan)
|
|
|
chan->ops->ready(chan);
|
|
|
}
|
|
|
|
|
|
+static void l2cap_start_connection(struct l2cap_chan *chan)
|
|
|
+{
|
|
|
+ if (__amp_capable(chan)) {
|
|
|
+ BT_DBG("chan %p AMP capable: discover AMPs", chan);
|
|
|
+ a2mp_discover_amp(chan);
|
|
|
+ } else {
|
|
|
+ l2cap_send_conn_req(chan);
|
|
|
+ }
|
|
|
+}
|
|
|
+
|
|
|
static void l2cap_do_start(struct l2cap_chan *chan)
|
|
|
{
|
|
|
struct l2cap_conn *conn = chan->conn;
|
|
@@ -986,8 +1008,9 @@ static void l2cap_do_start(struct l2cap_chan *chan)
|
|
|
return;
|
|
|
|
|
|
if (l2cap_chan_check_security(chan) &&
|
|
|
- __l2cap_no_conn_pending(chan))
|
|
|
- l2cap_send_conn_req(chan);
|
|
|
+ __l2cap_no_conn_pending(chan)) {
|
|
|
+ l2cap_start_connection(chan);
|
|
|
+ }
|
|
|
} else {
|
|
|
struct l2cap_info_req req;
|
|
|
req.type = __constant_cpu_to_le16(L2CAP_IT_FEAT_MASK);
|
|
@@ -1082,7 +1105,7 @@ static void l2cap_conn_start(struct l2cap_conn *conn)
|
|
|
continue;
|
|
|
}
|
|
|
|
|
|
- l2cap_send_conn_req(chan);
|
|
|
+ l2cap_start_connection(chan);
|
|
|
|
|
|
} else if (chan->state == BT_CONNECT2) {
|
|
|
struct l2cap_conn_rsp rsp;
|
|
@@ -5456,7 +5479,7 @@ int l2cap_security_cfm(struct hci_conn *hcon, u8 status, u8 encrypt)
|
|
|
|
|
|
if (chan->state == BT_CONNECT) {
|
|
|
if (!status) {
|
|
|
- l2cap_send_conn_req(chan);
|
|
|
+ l2cap_start_connection(chan);
|
|
|
} else {
|
|
|
__set_chan_timer(chan, L2CAP_DISC_TIMEOUT);
|
|
|
}
|