aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorSuraj Sumangala <suraj@atheros.com>2010-07-14 03:32:19 -0400
committerMarcel Holtmann <marcel@holtmann.org>2010-07-21 13:39:12 -0400
commit9981151086385eecc2febf4ba95a14593f834b3d (patch)
tree3cdda7fe4c3d5d3bf05e9ca6fb8f9f1b6ab1c226
parentf39a3c06404d01ef2ce47e821bc778dfb1836df9 (diff)
Bluetooth: Implemented HCI frame reassembly for RX from stream
Implemented frame reassembly implementation for reassembling fragments received from stream. Signed-off-by: Suraj Sumangala <suraj@atheros.com> Signed-off-by: Marcel Holtmann <marcel@holtmann.org>
-rw-r--r--include/net/bluetooth/hci_core.h1
-rw-r--r--net/bluetooth/hci_core.c35
2 files changed, 36 insertions, 0 deletions
diff --git a/include/net/bluetooth/hci_core.h b/include/net/bluetooth/hci_core.h
index 28e5eeefdec8..350b3e6964bd 100644
--- a/include/net/bluetooth/hci_core.h
+++ b/include/net/bluetooth/hci_core.h
@@ -437,6 +437,7 @@ void hci_event_packet(struct hci_dev *hdev, struct sk_buff *skb);
437 437
438int hci_recv_frame(struct sk_buff *skb); 438int hci_recv_frame(struct sk_buff *skb);
439int hci_recv_fragment(struct hci_dev *hdev, int type, void *data, int count); 439int hci_recv_fragment(struct hci_dev *hdev, int type, void *data, int count);
440int hci_recv_stream_fragment(struct hci_dev *hdev, void *data, int count);
440 441
441int hci_register_sysfs(struct hci_dev *hdev); 442int hci_register_sysfs(struct hci_dev *hdev);
442void hci_unregister_sysfs(struct hci_dev *hdev); 443void hci_unregister_sysfs(struct hci_dev *hdev);
diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c
index 451e266840ad..995c9f9b84d0 100644
--- a/net/bluetooth/hci_core.c
+++ b/net/bluetooth/hci_core.c
@@ -1163,6 +1163,41 @@ int hci_recv_fragment(struct hci_dev *hdev, int type, void *data, int count)
1163} 1163}
1164EXPORT_SYMBOL(hci_recv_fragment); 1164EXPORT_SYMBOL(hci_recv_fragment);
1165 1165
1166#define STREAM_REASSEMBLY 0
1167
1168int hci_recv_stream_fragment(struct hci_dev *hdev, void *data, int count)
1169{
1170 int type;
1171 int rem = 0;
1172
1173 do {
1174 struct sk_buff *skb = hdev->reassembly[STREAM_REASSEMBLY];
1175
1176 if (!skb) {
1177 struct { char type; } *pkt;
1178
1179 /* Start of the frame */
1180 pkt = data;
1181 type = pkt->type;
1182
1183 data++;
1184 count--;
1185 } else
1186 type = bt_cb(skb)->pkt_type;
1187
1188 rem = hci_reassembly(hdev, type, data,
1189 count, STREAM_REASSEMBLY, GFP_ATOMIC);
1190 if (rem < 0)
1191 return rem;
1192
1193 data += (count - rem);
1194 count = rem;
1195 } while (count);
1196
1197 return rem;
1198}
1199EXPORT_SYMBOL(hci_recv_stream_fragment);
1200
1166/* ---- Interface to upper protocols ---- */ 1201/* ---- Interface to upper protocols ---- */
1167 1202
1168/* Register/Unregister protocols. 1203/* Register/Unregister protocols.