xref: /btstack/src/l2cap.c (revision 645658c9de1b07ed00d498d8a09568bcf54a32ff)
1 /*
2  * Copyright (C) 2009 by Matthias Ringwald
3  *
4  * Redistribution and use in source and binary forms, with or without
5  * modification, are permitted provided that the following conditions
6  * are met:
7  *
8  * 1. Redistributions of source code must retain the above copyright
9  *    notice, this list of conditions and the following disclaimer.
10  * 2. Redistributions in binary form must reproduce the above copyright
11  *    notice, this list of conditions and the following disclaimer in the
12  *    documentation and/or other materials provided with the distribution.
13  * 3. Neither the name of the copyright holders nor the names of
14  *    contributors may be used to endorse or promote products derived
15  *    from this software without specific prior written permission.
16  *
17  * THIS SOFTWARE IS PROVIDED BY MATTHIAS RINGWALD AND CONTRIBUTORS
18  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
19  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
20  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL MATTHIAS
21  * RINGWALD OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
22  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
23  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
24  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
25  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
26  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
27  * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
28  * SUCH DAMAGE.
29  *
30  */
31 
32 /*
33  *  l2cap.c
34  *
35  *  Logical Link Control and Adaption Protocl (L2CAP)
36  *
37  *  Created by Matthias Ringwald on 5/16/09.
38  */
39 
40 #include "l2cap.h"
41 #include "hci.h"
42 
43 #include <stdarg.h>
44 #include <string.h>
45 
46 #include <stdio.h>
47 
48 // size of HCI ACL + L2CAP Header for regular data packets
49 #define COMPLETE_L2CAP_HEADER 8
50 
51 static void null_event_handler(uint8_t *packet, uint16_t size);
52 static void null_data_handler(uint16_t source_cid, uint8_t *packet, uint16_t size);
53 
54 static uint8_t * sig_buffer = NULL;
55 static linked_list_t l2cap_channels = NULL;
56 static linked_list_t l2cap_services = NULL;
57 static uint8_t * acl_buffer = NULL;
58 static void (*event_packet_handler) (uint8_t *packet, uint16_t size) = null_event_handler;
59 static void (*data_packet_handler)  (uint16_t source_cid, uint8_t *packet, uint16_t size) = null_data_handler;
60 static connection_t * capture_connection = NULL;
61 
62 void l2cap_init(){
63     sig_buffer = malloc( 48 );
64     acl_buffer = malloc( 255 + 8 );
65 
66     //
67     // register callbacks with HCI
68     //
69     hci_register_event_packet_handler(&l2cap_event_handler);
70     hci_register_acl_packet_handler(&l2cap_acl_handler);
71 }
72 
73 
74 /** Register L2CAP packet handlers */
75 static void null_event_handler(uint8_t *packet, uint16_t size){
76 }
77 static void null_data_handler(uint16_t  source_cid, uint8_t *packet, uint16_t size){
78 }
79 void l2cap_register_event_packet_handler(void (*handler)(uint8_t *packet, uint16_t size)){
80     event_packet_handler = handler;
81 }
82 void l2cap_register_data_packet_handler  (void (*handler)(uint16_t source_cid, uint8_t *packet, uint16_t size)){
83     data_packet_handler = handler;
84 }
85 
86 int l2cap_send_signaling_packet(hci_con_handle_t handle, L2CAP_SIGNALING_COMMANDS cmd, uint8_t identifier, ...){
87     va_list argptr;
88     va_start(argptr, identifier);
89     uint16_t len = l2cap_create_signaling_internal(sig_buffer, handle, cmd, identifier, argptr);
90     va_end(argptr);
91     return hci_send_acl_packet(sig_buffer, len);
92 }
93 
94 l2cap_channel_t * l2cap_get_channel_for_source_cid(uint16_t source_cid){
95     linked_item_t *it;
96     l2cap_channel_t * channel;
97     for (it = (linked_item_t *) l2cap_channels; it ; it = it->next){
98         channel = (l2cap_channel_t *) it;
99         if ( channel->source_cid == source_cid) {
100             return channel;
101         }
102     }
103     return NULL;
104 }
105 
106 // open outgoing L2CAP channel
107 void l2cap_create_channel_internal(connection_t * connection, bd_addr_t address, uint16_t psm){
108 
109     // alloc structure
110     l2cap_channel_t * chan = malloc(sizeof(l2cap_channel_t));
111     // TODO: emit error event
112     if (!chan) return;
113 
114     // fill in
115     BD_ADDR_COPY(chan->address, address);
116     chan->psm = psm;
117     chan->handle = 0;
118     chan->connection = connection;
119 
120     // set initial state
121     chan->state = L2CAP_STATE_CLOSED;
122     chan->sig_id = L2CAP_SIG_ID_INVALID;
123 
124     // add to connections list
125     linked_list_add(&l2cap_channels, (linked_item_t *) chan);
126 
127     // send connection request
128     // BD_ADDR, Packet_Type, Page_Scan_Repetition_Mode, Reserved, Clock_Offset, Allow_Role_Switch
129     hci_send_cmd(&hci_create_connection, address, 0x18, 0, 0, 0, 0);
130 }
131 
132 void l2cap_disconnect_internal(uint16_t source_cid, uint8_t reason){
133     // find channel for source_cid
134     l2cap_channel_t * channel = l2cap_get_channel_for_source_cid(source_cid);
135     if (channel) {
136         channel->sig_id = l2cap_next_sig_id();
137         l2cap_send_signaling_packet( channel->handle, DISCONNECTION_REQUEST, channel->sig_id, channel->dest_cid, channel->source_cid);
138         channel->state = L2CAP_STATE_WAIT_DISCONNECT;
139     }
140 }
141 
142 static void l2cap_handle_connection_failed_for_addr(bd_addr_t address, uint8_t status){
143     linked_item_t *it;
144     for (it = (linked_item_t *) l2cap_channels; it ; it = it->next){
145         l2cap_channel_t * channel = (l2cap_channel_t *) it;
146         if ( ! BD_ADDR_CMP( channel->address, address) ){
147             if (channel->state == L2CAP_STATE_CLOSED) {
148                 // failure, forward error code
149                 l2cap_emit_channel_opened(channel, status);
150                 // discard channel
151                 linked_list_remove(&l2cap_channels, (linked_item_t *) channel);
152                 free (channel);
153             }
154         }
155     }
156 }
157 
158 static void l2cap_handle_connection_success_for_addr(bd_addr_t address, hci_con_handle_t handle){
159     linked_item_t *it;
160     for (it = (linked_item_t *) l2cap_channels; it ; it = it->next){
161         l2cap_channel_t * channel = (l2cap_channel_t *) it;
162         if ( ! BD_ADDR_CMP( channel->address, address) ){
163             if (channel->state == L2CAP_STATE_CLOSED) {
164                 // success, start l2cap handshake
165                 channel->handle = handle;
166                 channel->sig_id = l2cap_next_sig_id();
167                 channel->source_cid = l2cap_next_source_cid();
168                 channel->state = L2CAP_STATE_WAIT_CONNECT_RSP;
169                 l2cap_send_signaling_packet( channel->handle, CONNECTION_REQUEST, channel->sig_id, channel->psm, channel->source_cid);
170             }
171         }
172     }
173 }
174 
175 void l2cap_event_handler( uint8_t *packet, uint16_t size ){
176 
177     bd_addr_t address;
178     hci_con_handle_t handle;
179 
180     switch(packet[0]){
181 
182         // handle connection complete events
183         case HCI_EVENT_CONNECTION_COMPLETE:
184             bt_flip_addr(address, &packet[5]);
185             if (packet[2] == 0){
186                 handle = READ_BT_16(packet, 3);
187                 l2cap_handle_connection_success_for_addr(address, handle);
188             } else {
189                 l2cap_handle_connection_failed_for_addr(address, packet[2]);
190             }
191             break;
192 
193         // handle successful create connection cancel command
194         case HCI_EVENT_COMMAND_COMPLETE:
195             if ( COMMAND_COMPLETE_EVENT(packet, hci_create_connection_cancel) ) {
196                 if (packet[5] == 0){
197                     bt_flip_addr(address, &packet[6]);
198                     // CONNECTION TERMINATED BY LOCAL HOST (0X16)
199                     l2cap_handle_connection_failed_for_addr(address, 0x16);
200                 }
201             }
202             break;
203 
204         // handle disconnection complete events
205         case HCI_EVENT_DISCONNECTION_COMPLETE:
206             // send l2cap disconnect events for all channels on this handle
207             handle = READ_BT_16(packet, 3);
208             linked_item_t *it;
209             for (it = (linked_item_t *) l2cap_channels; it ; it = it->next){
210                 l2cap_channel_t * channel = (l2cap_channel_t *) it;
211                 if ( channel->handle == handle ){
212                     l2cap_finialize_channel_close(channel);
213                 }
214             }
215             break;
216 
217         // HCI Connection Timeouts
218         case L2CAP_EVENT_TIMEOUT_CHECK:
219             if (!capture_connection){
220                 hci_con_handle_t handle = READ_BT_16(packet, 2);
221                 linked_item_t *it;
222                 l2cap_channel_t * channel;
223                 int used = 0;
224                 for (it = (linked_item_t *) l2cap_channels; it ; it = it->next){
225                     channel = (l2cap_channel_t *) it;
226                     if (channel->handle == handle) {
227                         used = 1;
228                     }
229                 }
230                 if (!used) {
231                     hci_send_cmd(&hci_disconnect, handle, 0x13); // remote closed connection
232                 }
233             }
234             break;
235 
236         default:
237             break;
238     }
239 
240     // pass on
241     (*event_packet_handler)(packet, size);
242 }
243 
244 static void l2cap_handle_disconnect_request(l2cap_channel_t *channel, uint16_t identifier){
245     l2cap_send_signaling_packet( channel->handle, DISCONNECTION_RESPONSE, identifier, channel->dest_cid, channel->source_cid);
246     l2cap_finialize_channel_close(channel);
247 }
248 
249 static void l2cap_handle_connection_request(hci_con_handle_t handle, uint8_t sig_id, uint16_t psm, uint16_t dest_cid){
250 
251     l2cap_service_t *service = l2cap_get_service(psm);
252     if (!service) {
253         // 0x0002 PSM not supported
254         l2cap_send_signaling_packet(handle, CONNECTION_RESPONSE, sig_id, 0, 0, 0x0002, 0);
255         return;
256     }
257 
258     hci_connection_t * hci_connection = connection_for_handle( handle );
259     if (!hci_connection) {
260         printf("no hci_connection for handle %u", handle);
261         // TODO: emit error
262         return;
263     }
264 
265     // alloc structure
266     l2cap_channel_t * chan = malloc(sizeof(l2cap_channel_t));
267     // TODO: emit error event
268     if (!chan) return;
269 
270     // fill in
271     BD_ADDR_COPY(chan->address, hci_connection->address);
272     chan->psm = psm;
273     chan->handle = handle;
274     chan->connection = service->connection;
275     chan->source_cid = l2cap_next_source_cid();
276     chan->dest_cid   = dest_cid;
277 
278     // set initial state
279     chan->state = L2CAP_STATE_WAIT_CONFIG_REQ_RSP_OR_CONFIG_REQ;
280     chan->sig_id = sig_id;
281 
282     // add to connections list
283     linked_list_add(&l2cap_channels, (linked_item_t *) chan);
284 
285     // TODO: emit incoming connection request instead of answering directly
286 
287     l2cap_send_signaling_packet(handle, CONNECTION_RESPONSE, sig_id, dest_cid, chan->source_cid, 0, 0);
288 
289 }
290 
291 void l2cap_signaling_handler(l2cap_channel_t *channel, uint8_t *packet, uint16_t size){
292 
293     static uint8_t config_options[] = { 1, 2, 150, 0}; // mtu = 48
294 
295     uint8_t  code       = READ_L2CAP_SIGNALING_CODE( packet );
296     uint8_t  identifier = READ_L2CAP_SIGNALING_IDENTIFIER( packet );
297     uint16_t result = 0;
298 
299     switch (channel->state) {
300 
301         case L2CAP_STATE_WAIT_CONNECT_RSP:
302             switch (code){
303                 case CONNECTION_RESPONSE:
304                     result = READ_BT_16 (packet, L2CAP_SIGNALING_DATA_OFFSET+4);
305                     switch (result) {
306                         case 0:
307                             // successfull connection
308                             channel->dest_cid = READ_BT_16(packet, L2CAP_SIGNALING_DATA_OFFSET);
309                             channel->sig_id = l2cap_next_sig_id();
310                             l2cap_send_signaling_packet(channel->handle, CONFIGURE_REQUEST, channel->sig_id, channel->dest_cid, 0, 4, &config_options);
311                             channel->state = L2CAP_STATE_WAIT_CONFIG_REQ_RSP_OR_CONFIG_REQ;
312                             break;
313                         case 1:
314                             // connection pending. get some coffee
315                             break;
316                         default:
317                             // map l2cap connection response result to BTstack status enumeration
318                             l2cap_emit_channel_opened(channel, L2CAP_CONNECTION_RESPONSE_RESULT_SUCCESSFUL + result);
319                             break;
320                     }
321                     break;
322 
323                 case DISCONNECTION_REQUEST:
324                     l2cap_handle_disconnect_request(channel, identifier);
325                     break;
326 
327                 default:
328                     //@TODO: implement other signaling packets
329                     break;
330             }
331             break;
332 
333         case L2CAP_STATE_WAIT_CONFIG_REQ_RSP_OR_CONFIG_REQ:
334             switch (code) {
335                 case CONFIGURE_RESPONSE:
336                     channel->state = L2CAP_STATE_WAIT_CONFIG_REQ;
337                     break;
338                 case CONFIGURE_REQUEST:
339                     // accept the other's configuration options
340                     l2cap_send_signaling_packet(channel->handle, CONFIGURE_RESPONSE, identifier, channel->dest_cid, 0, 0, size - 16, &packet[16]);
341                     channel->state = L2CAP_STATE_WAIT_CONFIG_REQ_RSP;
342                     break;
343                 case DISCONNECTION_REQUEST:
344                     l2cap_handle_disconnect_request(channel, identifier);
345                     break;
346                 default:
347                     //@TODO: implement other signaling packets
348                     break;
349             }
350             break;
351 
352         case L2CAP_STATE_WAIT_CONFIG_REQ:
353             switch (code) {
354                 case CONFIGURE_REQUEST:
355                     // accept the other's configuration options
356                     l2cap_send_signaling_packet(channel->handle, CONFIGURE_RESPONSE, identifier, channel->dest_cid, 0, 0, size - 16, &packet[16]);
357                     channel->state = L2CAP_STATE_OPEN;
358                     l2cap_emit_channel_opened(channel, 0);  // success
359                     break;
360                 case DISCONNECTION_REQUEST:
361                     l2cap_handle_disconnect_request(channel, identifier);
362                     break;
363                 default:
364                     //@TODO: implement other signaling packets
365                     break;
366             }
367             break;
368 
369         case L2CAP_STATE_WAIT_CONFIG_REQ_RSP:
370             switch (code) {
371                 case CONFIGURE_RESPONSE:
372                     channel->state = L2CAP_STATE_OPEN;
373                     l2cap_emit_channel_opened(channel, 0);  // success
374                     break;
375                 case DISCONNECTION_REQUEST:
376                     l2cap_handle_disconnect_request(channel, identifier);
377                     break;
378                 default:
379                     //@TODO: implement other signaling packets
380                     break;
381             }
382             break;
383 
384         case L2CAP_STATE_WAIT_DISCONNECT:
385             switch (code) {
386                 case DISCONNECTION_RESPONSE:
387                     l2cap_finialize_channel_close(channel);
388                     break;
389                 case DISCONNECTION_REQUEST:
390                     l2cap_handle_disconnect_request(channel, identifier);
391                     break;
392                 default:
393                     //@TODO: implement other signaling packets
394                     break;
395             }
396             break;
397 
398         case L2CAP_STATE_CLOSED:
399             // @TODO handle incoming requests
400             break;
401 
402         case L2CAP_STATE_OPEN:
403             switch (code) {
404                 case DISCONNECTION_REQUEST:
405                     l2cap_handle_disconnect_request(channel, identifier);
406                     break;
407                 default:
408                     //@TODO: implement other signaling packets, e.g. re-configure
409                     break;
410             }
411             break;
412     }
413 }
414 
415 // finalize closed channel
416 void l2cap_finialize_channel_close(l2cap_channel_t *channel){
417     channel->state = L2CAP_STATE_CLOSED;
418     l2cap_emit_channel_closed(channel);
419 
420     // discard channel
421     linked_list_remove(&l2cap_channels, (linked_item_t *) channel);
422     free (channel);
423 }
424 
425 l2cap_service_t * l2cap_get_service(uint16_t psm){
426     linked_item_t *it;
427 
428     // close open channels
429     for (it = (linked_item_t *) l2cap_services; it ; it = it->next){
430         l2cap_service_t * service = ((l2cap_service_t *) it);
431         if ( service->psm == psm){
432             return service;
433         };
434     }
435     return NULL;
436 }
437 
438 void l2cap_register_service_internal(connection_t *connection, uint16_t psm, uint16_t mtu){
439     // check for alread registered psm // TODO: emit error event
440     l2cap_service_t *service = l2cap_get_service(psm);
441     if (service) return;
442 
443     // alloc structure     // TODO: emit error event
444     service = malloc(sizeof(l2cap_service_t));
445     if (!service) return;
446 
447     // fill in
448     service->psm = psm;
449     service->mtu = mtu;
450     service->connection = connection;
451 
452     // add to services list
453     linked_list_add(&l2cap_services, (linked_item_t *) service);
454 }
455 
456 void l2cap_unregister_service_internal(connection_t *connection, uint16_t psm){
457     l2cap_service_t *service = l2cap_get_service(psm);
458     if (service) return;
459     linked_list_remove(&l2cap_services, (linked_item_t *) service);
460     free( service );
461 }
462 
463 //
464 void l2cap_close_connection(connection_t *connection){
465     linked_item_t *it;
466 
467     // close open channels
468     l2cap_channel_t * channel;
469     for (it = (linked_item_t *) l2cap_channels; it ; it = it->next){
470         channel = (l2cap_channel_t *) it;
471         if (channel->connection == connection) {
472             channel->sig_id = l2cap_next_sig_id();
473             l2cap_send_signaling_packet( channel->handle, DISCONNECTION_REQUEST, channel->sig_id, channel->dest_cid, channel->source_cid);
474             channel->state = L2CAP_STATE_WAIT_DISCONNECT;
475         }
476     }
477 
478     // unregister services
479     l2cap_service_t *service;
480     for (it = (linked_item_t *) &l2cap_services; it ; it = it->next){
481         channel = (l2cap_channel_t *) it->next;
482         if (service->connection == connection){
483             it->next = it->next->next;
484             return;
485         }
486     }
487 }
488 
489 void l2cap_accept_connection_internal(hci_con_handle_t handle,  uint16_t dest_cid){
490     printf("l2cap_accept_connection_internal called but not implemented yet 0x%x, 0x%x\n", handle, dest_cid);
491 }
492 
493 void l2cap_decline_connection_internal(hci_con_handle_t handle, uint16_t dest_cid, uint8_t reason){
494     printf("l2cap_decline_connection_internal called but not implemented yet 0x%x, 0x%x, %u", handle, dest_cid,reason);
495 }
496 
497 //  notify client
498 void l2cap_emit_channel_opened(l2cap_channel_t *channel, uint8_t status) {
499     uint8_t event[17];
500     event[0] = L2CAP_EVENT_CHANNEL_OPENED;
501     event[1] = sizeof(event) - 2;
502     event[2] = status;
503     bt_flip_addr(&event[3], channel->address);
504     bt_store_16(event,  9, channel->handle);
505     bt_store_16(event, 11, channel->psm);
506     bt_store_16(event, 13, channel->source_cid);
507     bt_store_16(event, 15, channel->dest_cid);
508     socket_connection_send_packet(channel->connection, HCI_EVENT_PACKET, 0, event, sizeof(event));
509 }
510 
511 void l2cap_emit_channel_closed(l2cap_channel_t *channel) {
512     uint8_t event[4];
513     event[0] = L2CAP_EVENT_CHANNEL_CLOSED;
514     event[1] = sizeof(event) - 2;
515     bt_store_16(event, 2, channel->source_cid);
516     socket_connection_send_packet(channel->connection, HCI_EVENT_PACKET, 0, event, sizeof(event));
517 }
518 
519 void l2cap_acl_handler( uint8_t *packet, uint16_t size ){
520 
521     // Capturing?
522     if (capture_connection) {
523         socket_connection_send_packet(capture_connection, HCI_ACL_DATA_PACKET, 0, packet, size);
524         return;
525     }
526 
527     // forward to higher layers - not needed yet
528     // (*data_packet_handler)(channel_id, packet, size);
529 
530     // Get Channel ID and command code
531     uint16_t channel_id = READ_L2CAP_CHANNEL_ID(packet);
532     uint8_t  code       = READ_L2CAP_SIGNALING_CODE( packet );
533 
534     // Get Connection
535     hci_con_handle_t handle = READ_ACL_CONNECTION_HANDLE(packet);
536 
537     // Signaling Packet?
538     if (channel_id == 1) {
539 
540         if (code < 1 || code == 2 || code >= 8){
541             // not for a particular channel
542             return;
543         }
544 
545         // Get Signaling Identifier
546         uint8_t sig_id    = READ_L2CAP_SIGNALING_IDENTIFIER(packet);
547 
548         // CONNECTION_REQUEST
549         if (code == CONNECTION_REQUEST){
550             uint16_t psm =      READ_BT_16(packet, L2CAP_SIGNALING_DATA_OFFSET);
551             uint16_t dest_cid = READ_BT_16(packet, L2CAP_SIGNALING_DATA_OFFSET+2);
552             l2cap_handle_connection_request(handle, sig_id, psm, dest_cid);
553             return;
554         }
555 
556         // Get potential destination CID
557         uint16_t dest_cid = READ_BT_16(packet, L2CAP_SIGNALING_DATA_OFFSET);
558 
559         // Find channel for this sig_id and connection handle
560         linked_item_t *it;
561         for (it = (linked_item_t *) l2cap_channels; it ; it = it->next){
562             l2cap_channel_t * channel = (l2cap_channel_t *) it;
563             if (channel->handle == handle) {
564                 if (code & 1) {
565                     // match odd commands by previous signaling identifier
566                     if (channel->sig_id == sig_id) {
567                         l2cap_signaling_handler( channel, packet, size);
568                     }
569                 } else {
570                     // match even commands by source channel id
571                     if (channel->source_cid == dest_cid) {
572                         l2cap_signaling_handler( channel, packet, size);
573                     }
574                 }
575             }
576         }
577         return;
578     }
579 
580     // Find channel for this channel_id and connection handle
581     l2cap_channel_t * channel = l2cap_get_channel_for_source_cid(channel_id);
582     if (channel) {
583         socket_connection_send_packet(channel->connection, L2CAP_DATA_PACKET, channel_id,
584                                       &packet[COMPLETE_L2CAP_HEADER], size-COMPLETE_L2CAP_HEADER);
585     }
586 }
587 
588 
589 void l2cap_send_internal(uint16_t source_cid, uint8_t *data, uint16_t len){
590     // find channel for source_cid, construct l2cap packet and send
591     l2cap_channel_t * channel = l2cap_get_channel_for_source_cid(source_cid);
592     if (channel) {
593          // 0 - Connection handle : PB=10 : BC=00
594          bt_store_16(acl_buffer, 0, channel->handle | (2 << 12) | (0 << 14));
595          // 2 - ACL length
596          bt_store_16(acl_buffer, 2,  len + 4);
597          // 4 - L2CAP packet length
598          bt_store_16(acl_buffer, 4,  len + 0);
599          // 6 - L2CAP channel DEST
600          bt_store_16(acl_buffer, 6, channel->dest_cid);
601          // 8 - data
602          memcpy(&acl_buffer[8], data, len);
603          // send
604          hci_send_acl_packet(acl_buffer, len+8);
605      }
606 }
607 
608 void l2cap_set_capture_connection(connection_t * connection){
609     capture_connection = connection;
610 }
611 
612