Commit aef89f21 authored by Szymon Janc's avatar Szymon Janc Committed by Gustavo F. Padovan

Bluetooth: Fix possible NULL pointer derefence in l2cap code

Due to ERTM reliability L2CAP channel needs to be disconnected if
adding to srej list failed.
Signed-off-by: default avatarSzymon Janc <szymon.janc@tieto.com>
Signed-off-by: default avatarGustavo F. Padovan <padovan@profusion.mobi>
parent 36acbb1a
...@@ -3788,7 +3788,7 @@ static void l2cap_resend_srejframe(struct l2cap_chan *chan, u16 tx_seq) ...@@ -3788,7 +3788,7 @@ static void l2cap_resend_srejframe(struct l2cap_chan *chan, u16 tx_seq)
} }
} }
static void l2cap_send_srejframe(struct l2cap_chan *chan, u16 tx_seq) static int l2cap_send_srejframe(struct l2cap_chan *chan, u16 tx_seq)
{ {
struct srej_list *new; struct srej_list *new;
u32 control; u32 control;
...@@ -3799,6 +3799,9 @@ static void l2cap_send_srejframe(struct l2cap_chan *chan, u16 tx_seq) ...@@ -3799,6 +3799,9 @@ static void l2cap_send_srejframe(struct l2cap_chan *chan, u16 tx_seq)
l2cap_send_sframe(chan, control); l2cap_send_sframe(chan, control);
new = kzalloc(sizeof(struct srej_list), GFP_ATOMIC); new = kzalloc(sizeof(struct srej_list), GFP_ATOMIC);
if (!new)
return -ENOMEM;
new->tx_seq = chan->expected_tx_seq; new->tx_seq = chan->expected_tx_seq;
chan->expected_tx_seq = __next_seq(chan, chan->expected_tx_seq); chan->expected_tx_seq = __next_seq(chan, chan->expected_tx_seq);
...@@ -3807,6 +3810,8 @@ static void l2cap_send_srejframe(struct l2cap_chan *chan, u16 tx_seq) ...@@ -3807,6 +3810,8 @@ static void l2cap_send_srejframe(struct l2cap_chan *chan, u16 tx_seq)
} }
chan->expected_tx_seq = __next_seq(chan, chan->expected_tx_seq); chan->expected_tx_seq = __next_seq(chan, chan->expected_tx_seq);
return 0;
} }
static inline int l2cap_data_channel_iframe(struct l2cap_chan *chan, u32 rx_control, struct sk_buff *skb) static inline int l2cap_data_channel_iframe(struct l2cap_chan *chan, u32 rx_control, struct sk_buff *skb)
...@@ -3877,7 +3882,12 @@ static inline int l2cap_data_channel_iframe(struct l2cap_chan *chan, u32 rx_cont ...@@ -3877,7 +3882,12 @@ static inline int l2cap_data_channel_iframe(struct l2cap_chan *chan, u32 rx_cont
return 0; return 0;
} }
} }
l2cap_send_srejframe(chan, tx_seq);
err = l2cap_send_srejframe(chan, tx_seq);
if (err < 0) {
l2cap_send_disconn_req(chan->conn, chan, -err);
return err;
}
} }
} else { } else {
expected_tx_seq_offset = __seq_offset(chan, expected_tx_seq_offset = __seq_offset(chan,
...@@ -3899,7 +3909,11 @@ static inline int l2cap_data_channel_iframe(struct l2cap_chan *chan, u32 rx_cont ...@@ -3899,7 +3909,11 @@ static inline int l2cap_data_channel_iframe(struct l2cap_chan *chan, u32 rx_cont
set_bit(CONN_SEND_PBIT, &chan->conn_state); set_bit(CONN_SEND_PBIT, &chan->conn_state);
l2cap_send_srejframe(chan, tx_seq); err = l2cap_send_srejframe(chan, tx_seq);
if (err < 0) {
l2cap_send_disconn_req(chan->conn, chan, -err);
return err;
}
__clear_ack_timer(chan); __clear_ack_timer(chan);
} }
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment