aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMat Martineau <mathewm@codeaurora.org>2012-10-23 18:24:19 -0400
committerGustavo Padovan <gustavo.padovan@collabora.co.uk>2012-10-23 22:24:56 -0400
commitb99e13ade709274104f5c2b8a26dc7d2953fc58e (patch)
tree02b2c027ce44f1d2eaef6bb50145c5c3c5a28a38
parentd5f8a75d88ecef3987158a94e8070bdfb46b09bd (diff)
Bluetooth: Do not send data during channel move
Outgoing ERTM data is queued during a channel move. The ERTM state machine is partially reset at the start of a move, and must be resynchronized with the remote state machine at the end of the move. Data is not sent so that there are no state transitions between the partial reset and the resync. Streaming mode frames are dropped during a move. Signed-off-by: Mat Martineau <mathewm@codeaurora.org> Acked-by: Marcel Holtmann <marcel@holtmann.org> Acked-by: Andrei Emeltchenko <andrei.emeltchenko@intel.com> Signed-off-by: Gustavo Padovan <gustavo.padovan@collabora.co.uk>
-rw-r--r--net/bluetooth/l2cap_core.c12
1 files changed, 12 insertions, 0 deletions
diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c
index 22f3768aa0be..4eb3ca84de2f 100644
--- a/net/bluetooth/l2cap_core.c
+++ b/net/bluetooth/l2cap_core.c
@@ -947,6 +947,9 @@ static void l2cap_send_sframe(struct l2cap_chan *chan,
947 if (!control->sframe) 947 if (!control->sframe)
948 return; 948 return;
949 949
950 if (__chan_is_moving(chan))
951 return;
952
950 if (test_and_clear_bit(CONN_SEND_FBIT, &chan->conn_state) && 953 if (test_and_clear_bit(CONN_SEND_FBIT, &chan->conn_state) &&
951 !control->poll) 954 !control->poll)
952 control->final = 1; 955 control->final = 1;
@@ -1811,6 +1814,9 @@ static void l2cap_streaming_send(struct l2cap_chan *chan,
1811 1814
1812 BT_DBG("chan %p, skbs %p", chan, skbs); 1815 BT_DBG("chan %p, skbs %p", chan, skbs);
1813 1816
1817 if (__chan_is_moving(chan))
1818 return;
1819
1814 skb_queue_splice_tail_init(skbs, &chan->tx_q); 1820 skb_queue_splice_tail_init(skbs, &chan->tx_q);
1815 1821
1816 while (!skb_queue_empty(&chan->tx_q)) { 1822 while (!skb_queue_empty(&chan->tx_q)) {
@@ -1853,6 +1859,9 @@ static int l2cap_ertm_send(struct l2cap_chan *chan)
1853 if (test_bit(CONN_REMOTE_BUSY, &chan->conn_state)) 1859 if (test_bit(CONN_REMOTE_BUSY, &chan->conn_state))
1854 return 0; 1860 return 0;
1855 1861
1862 if (__chan_is_moving(chan))
1863 return 0;
1864
1856 while (chan->tx_send_head && 1865 while (chan->tx_send_head &&
1857 chan->unacked_frames < chan->remote_tx_win && 1866 chan->unacked_frames < chan->remote_tx_win &&
1858 chan->tx_state == L2CAP_TX_STATE_XMIT) { 1867 chan->tx_state == L2CAP_TX_STATE_XMIT) {
@@ -1918,6 +1927,9 @@ static void l2cap_ertm_resend(struct l2cap_chan *chan)
1918 if (test_bit(CONN_REMOTE_BUSY, &chan->conn_state)) 1927 if (test_bit(CONN_REMOTE_BUSY, &chan->conn_state))
1919 return; 1928 return;
1920 1929
1930 if (__chan_is_moving(chan))
1931 return;
1932
1921 while (chan->retrans_list.head != L2CAP_SEQ_LIST_CLEAR) { 1933 while (chan->retrans_list.head != L2CAP_SEQ_LIST_CLEAR) {
1922 seq = l2cap_seq_list_pop(&chan->retrans_list); 1934 seq = l2cap_seq_list_pop(&chan->retrans_list);
1923 1935