xref: /btstack/src/classic/hfp.c (revision bdf6d26abc1b93e8c1e8665fb025fb5d370ff36e)
1 /*
2  * Copyright (C) 2014 BlueKitchen GmbH
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  * 4. Any redistribution, use, or modification is done solely for
17  *    personal benefit and not for any commercial purpose or for
18  *    monetary gain.
19  *
20  * THIS SOFTWARE IS PROVIDED BY BLUEKITCHEN GMBH AND CONTRIBUTORS
21  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
22  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
23  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL MATTHIAS
24  * RINGWALD OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
25  * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
26  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
27  * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
28  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
29  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF
30  * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
31  * SUCH DAMAGE.
32  *
33  * Please inquire about commercial licensing options at
34  * [email protected]
35  *
36  */
37 
38 #define BTSTACK_FILE__ "hfp.c"
39 
40 
41 #include "btstack_config.h"
42 
43 #include <stdint.h>
44 #include <string.h>
45 #include <inttypes.h>
46 
47 #include "bluetooth_sdp.h"
48 #include "btstack_debug.h"
49 #include "btstack_event.h"
50 #include "btstack_memory.h"
51 #include "btstack_run_loop.h"
52 #include "classic/core.h"
53 #include "classic/sdp_client_rfcomm.h"
54 #include "classic/sdp_server.h"
55 #include "classic/sdp_util.h"
56 #include "classic/sdp_client.h"
57 #include "hci.h"
58 #include "hci_cmd.h"
59 #include "hci_dump.h"
60 #include "l2cap.h"
61 
62 #if defined(ENABLE_CC256X_ASSISTED_HFP) && !defined(ENABLE_SCO_OVER_PCM)
63 #error "Assisted HFP is only possible over PCM/I2S. Please add define: ENABLE_SCO_OVER_PCM"
64 #endif
65 
66 #if defined(ENABLE_BCM_PCM_WBS) && !defined(ENABLE_SCO_OVER_PCM)
67 #error "WBS for PCM is only possible over PCM/I2S. Please add define: ENABLE_SCO_OVER_PCM"
68 #endif
69 
70 #define HFP_HF_FEATURES_SIZE 10
71 #define HFP_AG_FEATURES_SIZE 12
72 
73 typedef struct {
74     hfp_role_t local_role;
75     bd_addr_t  remote_address;
76 } hfp_sdp_query_context_t;
77 
78 // globals
79 
80 static hfp_sdp_query_context_t sdp_query_context;
81 static btstack_context_callback_registration_t hfp_handle_sdp_client_query_request;
82 
83 static btstack_linked_list_t hfp_connections ;
84 
85 static btstack_packet_handler_t hfp_hf_callback;
86 static btstack_packet_handler_t hfp_ag_callback;
87 
88 static btstack_packet_handler_t hfp_hf_rfcomm_packet_handler;
89 static btstack_packet_handler_t hfp_ag_rfcomm_packet_handler;
90 
91 static hfp_connection_t * sco_establishment_active;
92 
93 static uint16_t hfp_allowed_sco_packet_types;
94 
95 // prototypes
96 static hfp_link_settings_t hfp_next_link_setting_for_connection(hfp_link_settings_t current_setting, hfp_connection_t * hfp_connection, uint8_t eSCO_S4_supported);
97 static void parse_sequence(hfp_connection_t * context);
98 
99 
100 static const char * hfp_hf_features[] = {
101         "EC and/or NR function",
102         "Three-way calling",
103         "CLI presentation capability",
104         "Voice recognition activation",
105         "Remote volume control",
106 
107         "Enhanced call status",
108         "Enhanced call control",
109 
110         "Codec negotiation",
111 
112         "HF Indicators",
113         "eSCO S4 (and T2) Settings Supported",
114         "Reserved for future definition"
115 };
116 
117 static const char * hfp_ag_features[] = {
118         "Three-way calling",
119         "EC and/or NR function",
120         "Voice recognition function",
121         "In-band ring tone capability",
122         "Attach a number to a voice tag",
123         "Ability to reject a call",
124         "Enhanced call status",
125         "Enhanced call control",
126         "Extended Error Result Codes",
127         "Codec negotiation",
128         "HF Indicators",
129         "eSCO S4 (and T2) Settings Supported",
130         "Reserved for future definition"
131 };
132 
133 static const char * hfp_enhanced_call_dir[] = {
134         "outgoing",
135         "incoming"
136 };
137 
138 static const char * hfp_enhanced_call_status[] = {
139         "active",
140         "held",
141         "outgoing dialing",
142         "outgoing alerting",
143         "incoming",
144         "incoming waiting",
145         "call held by response and hold"
146 };
147 
148 static const char * hfp_enhanced_call_mode[] = {
149         "voice",
150         "data",
151         "fax"
152 };
153 
154 static const char * hfp_enhanced_call_mpty[] = {
155         "not a conference call",
156         "conference call"
157 };
158 
159 const char * hfp_enhanced_call_dir2str(uint16_t index){
160     if (index <= HFP_ENHANCED_CALL_DIR_INCOMING) return hfp_enhanced_call_dir[index];
161     return "not defined";
162 }
163 
164 const char * hfp_enhanced_call_status2str(uint16_t index){
165     if (index <= HFP_ENHANCED_CALL_STATUS_CALL_HELD_BY_RESPONSE_AND_HOLD) return hfp_enhanced_call_status[index];
166     return "not defined";
167 }
168 
169 const char * hfp_enhanced_call_mode2str(uint16_t index){
170     if (index <= HFP_ENHANCED_CALL_MODE_FAX) return hfp_enhanced_call_mode[index];
171     return "not defined";
172 }
173 
174 const char * hfp_enhanced_call_mpty2str(uint16_t index){
175     if (index <= HFP_ENHANCED_CALL_MPTY_CONFERENCE_CALL) return hfp_enhanced_call_mpty[index];
176     return "not defined";
177 }
178 
179 static uint16_t hfp_parse_indicator_index(hfp_connection_t * hfp_connection){
180     uint16_t index = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
181 
182     if (index > HFP_MAX_NUM_INDICATORS){
183         log_info("ignoring invalid indicator index bigger then HFP_MAX_NUM_INDICATORS");
184         return HFP_MAX_NUM_INDICATORS - 1;
185     }
186 
187     // indicator index enumeration starts with 1, we substract 1 to store in array with starting index 0
188     if (index > 0){
189         index -= 1;
190     } else {
191         log_info("ignoring invalid indicator index 0");
192         return 0;
193     }
194     return index;
195 }
196 
197 static void hfp_next_indicators_index(hfp_connection_t * hfp_connection){
198     if (hfp_connection->parser_item_index < HFP_MAX_NUM_INDICATORS - 1){
199         hfp_connection->parser_item_index++;
200     } else {
201         log_info("Ignoring additional indicator");
202     }
203 }
204 
205 static void hfp_next_codec_index(hfp_connection_t * hfp_connection){
206     if (hfp_connection->parser_item_index < HFP_MAX_NUM_CODECS - 1){
207         hfp_connection->parser_item_index++;
208     } else {
209         log_info("Ignoring additional codec index");
210     }
211 }
212 
213 static void hfp_next_remote_call_services_index(hfp_connection_t * hfp_connection){
214     if (hfp_connection->remote_call_services_index < HFP_MAX_NUM_CALL_SERVICES - 1){
215         hfp_connection->remote_call_services_index++;
216     } else {
217         log_info("Ignoring additional remote_call_services");
218     }
219 }
220 
221 const char * hfp_hf_feature(int index){
222     if (index > HFP_HF_FEATURES_SIZE){
223         return hfp_hf_features[HFP_HF_FEATURES_SIZE];
224     }
225     return hfp_hf_features[index];
226 }
227 
228 const char * hfp_ag_feature(int index){
229     if (index > HFP_AG_FEATURES_SIZE){
230         return hfp_ag_features[HFP_AG_FEATURES_SIZE];
231     }
232     return hfp_ag_features[index];
233 }
234 
235 int send_str_over_rfcomm(uint16_t cid, char * command){
236     if (!rfcomm_can_send_packet_now(cid)) return 1;
237     log_info("HFP_TX %s", command);
238     int err = rfcomm_send(cid, (uint8_t*) command, strlen(command));
239     if (err){
240         log_error("rfcomm_send -> error 0x%02x \n", err);
241     }
242 #ifdef ENABLE_HFP_AT_MESSAGES
243     hfp_connection_t * hfp_connection = get_hfp_connection_context_for_rfcomm_cid(cid);
244     hfp_emit_string_event(hfp_connection, HFP_SUBEVENT_AT_MESSAGE_SENT, command);
245 #endif
246     return 1;
247 }
248 
249 int hfp_supports_codec(uint8_t codec, int codecs_nr, uint8_t * codecs){
250 
251     // mSBC requires support for eSCO connections
252     if ((codec == HFP_CODEC_MSBC) && !hci_extended_sco_link_supported()) return 0;
253 
254     int i;
255     for (i = 0; i < codecs_nr; i++){
256         if (codecs[i] != codec) continue;
257         return 1;
258     }
259     return 0;
260 }
261 
262 void hfp_hf_drop_mSBC_if_eSCO_not_supported(uint8_t * codecs, uint8_t * codecs_nr){
263     if (hci_extended_sco_link_supported()) return;
264     uint8_t tmp_codecs[HFP_MAX_NUM_CODECS];
265     int i;
266     int tmp_codec_nr = 0;
267     for (i=0; i < *codecs_nr; i++){
268         if (codecs[i] == HFP_CODEC_MSBC) continue;
269         tmp_codecs[tmp_codec_nr++] = codecs[i];
270     }
271     *codecs_nr = tmp_codec_nr;
272     (void)memcpy(codecs, tmp_codecs, tmp_codec_nr);
273 }
274 
275 // UTILS
276 int get_bit(uint16_t bitmap, int position){
277     return (bitmap >> position) & 1;
278 }
279 
280 int store_bit(uint32_t bitmap, int position, uint8_t value){
281     if (value){
282         bitmap |= 1 << position;
283     } else {
284         bitmap &= ~ (1 << position);
285     }
286     return bitmap;
287 }
288 
289 int join(char * buffer, int buffer_size, uint8_t * values, int values_nr){
290     if (buffer_size < (values_nr * 3)) return 0;
291     int i;
292     int offset = 0;
293     for (i = 0; i < (values_nr-1); i++) {
294       offset += snprintf(buffer+offset, buffer_size-offset, "%d,", values[i]); // puts string into buffer
295     }
296     if (i<values_nr){
297         offset += snprintf(buffer+offset, buffer_size-offset, "%d", values[i]);
298     }
299     return offset;
300 }
301 
302 int join_bitmap(char * buffer, int buffer_size, uint32_t values, int values_nr){
303     if (buffer_size < (values_nr * 3)) return 0;
304 
305     int i;
306     int offset = 0;
307     for (i = 0; i < (values_nr-1); i++) {
308       offset += snprintf(buffer+offset, buffer_size-offset, "%d,", get_bit(values,i)); // puts string into buffer
309     }
310 
311     if (i<values_nr){
312         offset += snprintf(buffer+offset, buffer_size-offset, "%d", get_bit(values,i));
313     }
314     return offset;
315 }
316 
317 static void hfp_emit_event_for_context(hfp_connection_t * hfp_connection, uint8_t * packet, uint16_t size){
318     if (!hfp_connection) return;
319     btstack_packet_handler_t callback = NULL;
320     switch (hfp_connection->local_role){
321         case HFP_ROLE_HF:
322             callback = hfp_hf_callback;
323             break;
324         case HFP_ROLE_AG:
325             callback = hfp_ag_callback;
326             break;
327         default:
328             return;
329     }
330     (*callback)(HCI_EVENT_PACKET, 0, packet, size);
331 }
332 
333 void hfp_emit_simple_event(hfp_connection_t * hfp_connection, uint8_t event_subtype){
334     uint8_t event[5];
335     event[0] = HCI_EVENT_HFP_META;
336     event[1] = sizeof(event) - 2;
337     event[2] = event_subtype;
338     little_endian_store_16(event, 3, hfp_connection->acl_handle);
339     hfp_emit_event_for_context(hfp_connection, event, sizeof(event));
340 }
341 
342 void hfp_emit_event(hfp_connection_t * hfp_connection, uint8_t event_subtype, uint8_t value){
343     uint8_t event[6];
344     event[0] = HCI_EVENT_HFP_META;
345     event[1] = sizeof(event) - 2;
346     event[2] = event_subtype;
347     little_endian_store_16(event, 3, hfp_connection->acl_handle);
348     event[5] = value; // status 0 == OK
349     hfp_emit_event_for_context(hfp_connection, event, sizeof(event));
350 }
351 
352 void hfp_emit_slc_connection_event(hfp_connection_t * hfp_connection, uint8_t status, hci_con_handle_t con_handle, bd_addr_t addr){
353     uint8_t event[12];
354     int pos = 0;
355     event[pos++] = HCI_EVENT_HFP_META;
356     event[pos++] = sizeof(event) - 2;
357     event[pos++] = HFP_SUBEVENT_SERVICE_LEVEL_CONNECTION_ESTABLISHED;
358     event[pos++] = status; // status 0 == OK
359     little_endian_store_16(event, pos, con_handle);
360     pos += 2;
361     reverse_bd_addr(addr,&event[pos]);
362     pos += 6;
363     hfp_emit_event_for_context(hfp_connection, event, sizeof(event));
364 }
365 
366 static void hfp_emit_audio_connection_released(hfp_connection_t * hfp_connection, hci_con_handle_t sco_handle){
367     uint8_t event[7];
368     int pos = 0;
369     event[pos++] = HCI_EVENT_HFP_META;
370     event[pos++] = sizeof(event) - 2;
371     event[pos++] = HFP_SUBEVENT_AUDIO_CONNECTION_RELEASED;
372     little_endian_store_16(event, pos, hfp_connection->acl_handle);
373     pos += 2;
374     little_endian_store_16(event, pos, sco_handle);
375     pos += 2;
376     hfp_emit_event_for_context(hfp_connection, event, sizeof(event));
377 }
378 
379 void hfp_emit_sco_event(hfp_connection_t * hfp_connection, uint8_t status, hci_con_handle_t sco_handle, bd_addr_t addr, uint8_t  negotiated_codec){
380     uint8_t event[15];
381     int pos = 0;
382     event[pos++] = HCI_EVENT_HFP_META;
383     event[pos++] = sizeof(event) - 2;
384     event[pos++] = HFP_SUBEVENT_AUDIO_CONNECTION_ESTABLISHED;
385     little_endian_store_16(event, pos, hfp_connection->acl_handle);
386     pos += 2;
387     event[pos++] = status; // status 0 == OK
388     little_endian_store_16(event, pos, sco_handle);
389     pos += 2;
390     reverse_bd_addr(addr,&event[pos]);
391     pos += 6;
392     event[pos++] = negotiated_codec;
393     hfp_emit_event_for_context(hfp_connection, event, sizeof(event));
394 }
395 
396 void hfp_emit_string_event(hfp_connection_t * hfp_connection, uint8_t event_subtype, const char * value){
397 #ifdef ENABLE_HFP_AT_MESSAGES
398     uint8_t event[256];
399 #else
400     uint8_t event[40];
401 #endif
402     event[0] = HCI_EVENT_HFP_META;
403     event[1] = sizeof(event) - 2;
404     event[2] = event_subtype;
405     little_endian_store_16(event, 3, hfp_connection->acl_handle);
406     uint16_t size = btstack_min(strlen(value), sizeof(event) - 6);
407     strncpy((char*)&event[3], value, size);
408     event[5 + size] = 0;
409     hfp_emit_event_for_context(hfp_connection, event, sizeof(event));
410 }
411 
412 btstack_linked_list_t * hfp_get_connections(void){
413     return (btstack_linked_list_t *) &hfp_connections;
414 }
415 
416 hfp_connection_t * get_hfp_connection_context_for_rfcomm_cid(uint16_t cid){
417     btstack_linked_list_iterator_t it;
418     btstack_linked_list_iterator_init(&it, hfp_get_connections());
419     while (btstack_linked_list_iterator_has_next(&it)){
420         hfp_connection_t * hfp_connection = (hfp_connection_t *)btstack_linked_list_iterator_next(&it);
421         if (hfp_connection->rfcomm_cid == cid){
422             return hfp_connection;
423         }
424     }
425     return NULL;
426 }
427 
428 hfp_connection_t * get_hfp_connection_context_for_bd_addr(bd_addr_t bd_addr, hfp_role_t hfp_role){
429     btstack_linked_list_iterator_t it;
430     btstack_linked_list_iterator_init(&it, hfp_get_connections());
431     while (btstack_linked_list_iterator_has_next(&it)){
432         hfp_connection_t * hfp_connection = (hfp_connection_t *)btstack_linked_list_iterator_next(&it);
433         if ((memcmp(hfp_connection->remote_addr, bd_addr, 6) == 0) && (hfp_connection->local_role == hfp_role)) {
434             return hfp_connection;
435         }
436     }
437     return NULL;
438 }
439 
440 hfp_connection_t * get_hfp_connection_context_for_sco_handle(uint16_t handle, hfp_role_t hfp_role){
441     btstack_linked_list_iterator_t it;
442     btstack_linked_list_iterator_init(&it, hfp_get_connections());
443     while (btstack_linked_list_iterator_has_next(&it)){
444         hfp_connection_t * hfp_connection = (hfp_connection_t *)btstack_linked_list_iterator_next(&it);
445         if ((hfp_connection->sco_handle == handle) && (hfp_connection->local_role == hfp_role)){
446             return hfp_connection;
447         }
448     }
449     return NULL;
450 }
451 
452 hfp_connection_t * get_hfp_connection_context_for_acl_handle(uint16_t handle, hfp_role_t hfp_role){
453     btstack_linked_list_iterator_t it;
454     btstack_linked_list_iterator_init(&it, hfp_get_connections());
455     while (btstack_linked_list_iterator_has_next(&it)){
456         hfp_connection_t * hfp_connection = (hfp_connection_t *)btstack_linked_list_iterator_next(&it);
457         if ((hfp_connection->acl_handle == handle) && (hfp_connection->local_role == hfp_role)){
458             return hfp_connection;
459         }
460     }
461     return NULL;
462 }
463 
464 void hfp_reset_context_flags(hfp_connection_t * hfp_connection){
465     if (!hfp_connection) return;
466     hfp_connection->ok_pending = 0;
467     hfp_connection->send_error = 0;
468 
469     hfp_connection->found_equal_sign = false;
470 
471     hfp_connection->change_status_update_for_individual_ag_indicators = 0;
472     hfp_connection->operator_name_changed = 0;
473 
474     hfp_connection->enable_extended_audio_gateway_error_report = 0;
475     hfp_connection->extended_audio_gateway_error = 0;
476 
477     // establish codecs hfp_connection
478     hfp_connection->suggested_codec = 0;
479     hfp_connection->negotiated_codec = 0;
480     hfp_connection->codec_confirmed = 0;
481 
482     hfp_connection->establish_audio_connection = 0;
483     hfp_connection->call_waiting_notification_enabled = 0;
484     hfp_connection->command = HFP_CMD_NONE;
485     hfp_connection->enable_status_update_for_ag_indicators = 0xFF;
486 }
487 
488 static hfp_connection_t * create_hfp_connection_context(void){
489     hfp_connection_t * hfp_connection = btstack_memory_hfp_connection_get();
490     if (!hfp_connection) return NULL;
491 
492     hfp_connection->state = HFP_IDLE;
493     hfp_connection->call_state = HFP_CALL_IDLE;
494     hfp_connection->codecs_state = HFP_CODECS_IDLE;
495 
496     hfp_connection->parser_state = HFP_PARSER_CMD_HEADER;
497     hfp_connection->command = HFP_CMD_NONE;
498 
499     hfp_connection->acl_handle = HCI_CON_HANDLE_INVALID;
500     hfp_connection->sco_handle = HCI_CON_HANDLE_INVALID;
501 
502     hfp_reset_context_flags(hfp_connection);
503 
504     btstack_linked_list_add(&hfp_connections, (btstack_linked_item_t*)hfp_connection);
505     return hfp_connection;
506 }
507 
508 void hfp_finalize_connection_context(hfp_connection_t * hfp_connection){
509     btstack_linked_list_remove(&hfp_connections, (btstack_linked_item_t*) hfp_connection);
510     btstack_memory_hfp_connection_free(hfp_connection);
511 }
512 
513 static hfp_connection_t * provide_hfp_connection_context_for_bd_addr(bd_addr_t bd_addr, hfp_role_t local_role){
514     hfp_connection_t * hfp_connection = get_hfp_connection_context_for_bd_addr(bd_addr, local_role);
515     if (hfp_connection) return  hfp_connection;
516     hfp_connection = create_hfp_connection_context();
517     (void)memcpy(hfp_connection->remote_addr, bd_addr, 6);
518     hfp_connection->local_role = local_role;
519     log_info("Create HFP context %p: role %u, addr %s", hfp_connection, local_role, bd_addr_to_str(bd_addr));
520 
521     return hfp_connection;
522 }
523 
524 /* @param network.
525  * 0 == no ability to reject a call.
526  * 1 == ability to reject a call.
527  */
528 
529 /* @param suported_features
530  * HF bit 0: EC and/or NR function (yes/no, 1 = yes, 0 = no)
531  * HF bit 1: Call waiting or three-way calling(yes/no, 1 = yes, 0 = no)
532  * HF bit 2: CLI presentation capability (yes/no, 1 = yes, 0 = no)
533  * HF bit 3: Voice recognition activation (yes/no, 1= yes, 0 = no)
534  * HF bit 4: Remote volume control (yes/no, 1 = yes, 0 = no)
535  * HF bit 5: Wide band speech (yes/no, 1 = yes, 0 = no)
536  */
537  /* Bit position:
538  * AG bit 0: Three-way calling (yes/no, 1 = yes, 0 = no)
539  * AG bit 1: EC and/or NR function (yes/no, 1 = yes, 0 = no)
540  * AG bit 2: Voice recognition function (yes/no, 1 = yes, 0 = no)
541  * AG bit 3: In-band ring tone capability (yes/no, 1 = yes, 0 = no)
542  * AG bit 4: Attach a phone number to a voice tag (yes/no, 1 = yes, 0 = no)
543  * AG bit 5: Wide band speech (yes/no, 1 = yes, 0 = no)
544  */
545 
546 void hfp_create_sdp_record(uint8_t * service, uint32_t service_record_handle, uint16_t service_uuid, int rfcomm_channel_nr, const char * name){
547     uint8_t* attribute;
548     de_create_sequence(service);
549 
550     // 0x0000 "Service Record Handle"
551     de_add_number(service, DE_UINT, DE_SIZE_16, BLUETOOTH_ATTRIBUTE_SERVICE_RECORD_HANDLE);
552     de_add_number(service, DE_UINT, DE_SIZE_32, service_record_handle);
553 
554     // 0x0001 "Service Class ID List"
555     de_add_number(service,  DE_UINT, DE_SIZE_16, BLUETOOTH_ATTRIBUTE_SERVICE_CLASS_ID_LIST);
556     attribute = de_push_sequence(service);
557     {
558         //  "UUID for Service"
559         de_add_number(attribute, DE_UUID, DE_SIZE_16, service_uuid);
560         de_add_number(attribute, DE_UUID, DE_SIZE_16, BLUETOOTH_SERVICE_CLASS_GENERIC_AUDIO);
561     }
562     de_pop_sequence(service, attribute);
563 
564     // 0x0004 "Protocol Descriptor List"
565     de_add_number(service,  DE_UINT, DE_SIZE_16, BLUETOOTH_ATTRIBUTE_PROTOCOL_DESCRIPTOR_LIST);
566     attribute = de_push_sequence(service);
567     {
568         uint8_t* l2cpProtocol = de_push_sequence(attribute);
569         {
570             de_add_number(l2cpProtocol,  DE_UUID, DE_SIZE_16, BLUETOOTH_PROTOCOL_L2CAP);
571         }
572         de_pop_sequence(attribute, l2cpProtocol);
573 
574         uint8_t* rfcomm = de_push_sequence(attribute);
575         {
576             de_add_number(rfcomm,  DE_UUID, DE_SIZE_16, BLUETOOTH_PROTOCOL_RFCOMM);  // rfcomm_service
577             de_add_number(rfcomm,  DE_UINT, DE_SIZE_8,  rfcomm_channel_nr);  // rfcomm channel
578         }
579         de_pop_sequence(attribute, rfcomm);
580     }
581     de_pop_sequence(service, attribute);
582 
583 
584     // 0x0005 "Public Browse Group"
585     de_add_number(service,  DE_UINT, DE_SIZE_16, BLUETOOTH_ATTRIBUTE_BROWSE_GROUP_LIST); // public browse group
586     attribute = de_push_sequence(service);
587     {
588         de_add_number(attribute,  DE_UUID, DE_SIZE_16, BLUETOOTH_ATTRIBUTE_PUBLIC_BROWSE_ROOT);
589     }
590     de_pop_sequence(service, attribute);
591 
592     // 0x0009 "Bluetooth Profile Descriptor List"
593     de_add_number(service,  DE_UINT, DE_SIZE_16, BLUETOOTH_ATTRIBUTE_BLUETOOTH_PROFILE_DESCRIPTOR_LIST);
594     attribute = de_push_sequence(service);
595     {
596         uint8_t *sppProfile = de_push_sequence(attribute);
597         {
598             de_add_number(sppProfile,  DE_UUID, DE_SIZE_16, BLUETOOTH_SERVICE_CLASS_HANDSFREE);
599             de_add_number(sppProfile,  DE_UINT, DE_SIZE_16, 0x0107); // Verision 1.7
600         }
601         de_pop_sequence(attribute, sppProfile);
602     }
603     de_pop_sequence(service, attribute);
604 
605     // 0x0100 "Service Name"
606     de_add_number(service,  DE_UINT, DE_SIZE_16, 0x0100);
607     de_add_data(service,  DE_STRING, strlen(name), (uint8_t *) name);
608 }
609 
610 static void handle_query_rfcomm_event(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size){
611     UNUSED(packet_type);    // ok: handling own sdp events
612     UNUSED(channel);        // ok: no channel
613     UNUSED(size);           // ok: handling own sdp events
614 
615     hfp_connection_t * hfp_connection = get_hfp_connection_context_for_bd_addr(sdp_query_context.remote_address, sdp_query_context.local_role);
616     if (hfp_connection == NULL) {
617         log_info("connection with %s and local role %d not found", sdp_query_context.remote_address, sdp_query_context.local_role);
618         return;
619     }
620 
621     switch (hci_event_packet_get_type(packet)){
622         case SDP_EVENT_QUERY_RFCOMM_SERVICE:
623             hfp_connection->rfcomm_channel_nr = sdp_event_query_rfcomm_service_get_rfcomm_channel(packet);
624             break;
625         case SDP_EVENT_QUERY_COMPLETE:
626             if (hfp_connection->rfcomm_channel_nr > 0){
627                 hfp_connection->state = HFP_W4_RFCOMM_CONNECTED;
628                 btstack_packet_handler_t packet_handler;
629                 switch (hfp_connection->local_role){
630                     case HFP_ROLE_AG:
631                         packet_handler = hfp_ag_rfcomm_packet_handler;
632                         break;
633                     case HFP_ROLE_HF:
634                         packet_handler = hfp_hf_rfcomm_packet_handler;
635                         break;
636                     default:
637                         btstack_assert(false);
638                         return;
639                 }
640 
641                 rfcomm_create_channel(packet_handler, hfp_connection->remote_addr, hfp_connection->rfcomm_channel_nr, NULL);
642 
643             } else {
644                 hfp_connection->state = HFP_IDLE;
645                 uint8_t status = sdp_event_query_complete_get_status(packet);
646                 if (status == ERROR_CODE_SUCCESS){
647                     // report service not found
648                     status = SDP_SERVICE_NOT_FOUND;
649                 }
650                 hfp_emit_slc_connection_event(hfp_connection, status, HCI_CON_HANDLE_INVALID, hfp_connection->remote_addr);
651                 log_info("rfcomm service not found, status 0x%02x", status);
652             }
653 
654             // register the SDP Query request to check if there is another connection waiting for the query
655             // ignore ERROR_CODE_COMMAND_DISALLOWED because in that case, we already have requested an SDP callback
656             (void) sdp_client_register_query_callback(&hfp_handle_sdp_client_query_request);
657             break;
658         default:
659             break;
660     }
661 }
662 
663 // returns 0 if unexpected error or no other link options remained, otherwise 1
664 static int hfp_handle_failed_sco_connection(uint8_t status){
665 
666     if (!sco_establishment_active){
667         log_info("(e)SCO Connection failed but not started by us");
668         return 0;
669     }
670 
671     log_info("(e)SCO Connection failed 0x%02x", status);
672     switch (status){
673         case ERROR_CODE_UNSUPPORTED_FEATURE_OR_PARAMETER_VALUE:
674         case ERROR_CODE_UNSPECIFIED_ERROR:
675         case ERROR_CODE_CONNECTION_REJECTED_DUE_TO_LIMITED_RESOURCES:
676             break;
677         default:
678             return 0;
679     }
680 
681     // note: eSCO_S4 supported flag not available, but it's only relevant for highest CVSD link setting (and the current failed)
682     hfp_link_settings_t next_setting = hfp_next_link_setting_for_connection(sco_establishment_active->link_setting, sco_establishment_active, false);
683 
684     // handle no valid setting found
685     if (next_setting == HFP_LINK_SETTINGS_NONE) {
686         if (sco_establishment_active->negotiated_codec == HFP_CODEC_MSBC){
687             log_info("T2/T1 failed, fallback to CVSD - D1");
688             sco_establishment_active->negotiated_codec = HFP_CODEC_CVSD;
689             sco_establishment_active->sco_for_msbc_failed = 1;
690             sco_establishment_active->command = HFP_CMD_AG_SEND_COMMON_CODEC;
691             sco_establishment_active->link_setting = HFP_LINK_SETTINGS_D1;
692         } else {
693             // no other options
694             return 0;
695         }
696     }
697 
698     log_info("e)SCO Connection: try new link_setting %d", next_setting);
699     sco_establishment_active->establish_audio_connection = 1;
700     sco_establishment_active->link_setting = next_setting;
701     sco_establishment_active = NULL;
702     return 1;
703 }
704 
705 
706 void hfp_handle_hci_event(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size, hfp_role_t local_role){
707     UNUSED(packet_type);
708     UNUSED(channel);    // ok: no channel
709     UNUSED(size);
710 
711     bd_addr_t event_addr;
712     hci_con_handle_t handle;
713     hfp_connection_t * hfp_connection = NULL;
714     uint8_t status;
715 
716     log_debug("HFP HCI event handler type %u, event type %x, size %u", packet_type, hci_event_packet_get_type(packet), size);
717 
718     switch (hci_event_packet_get_type(packet)) {
719 
720         case HCI_EVENT_CONNECTION_REQUEST:
721             switch(hci_event_connection_request_get_link_type(packet)){
722                 case 0: //  SCO
723                 case 2: // eSCO
724                     hci_event_connection_request_get_bd_addr(packet, event_addr);
725                     hfp_connection = get_hfp_connection_context_for_bd_addr(event_addr, local_role);
726                     if (!hfp_connection) break;
727                     if (hci_event_connection_request_get_link_type(packet) == 2){
728                         hfp_connection->hf_accept_sco = 2;
729                     } else {
730                         hfp_connection->hf_accept_sco = 1;
731                     }
732 #ifdef ENABLE_CC256X_ASSISTED_HFP
733                     hfp_cc256x_prepare_for_sco(hfp_connection);
734 #endif
735 #ifdef ENABLE_BCM_PCM_WBS
736                     hfp_bcm_prepare_for_sco(hfp_connection);
737 #endif
738                     log_info("hf accept sco %u\n", hfp_connection->hf_accept_sco);
739                     sco_establishment_active = hfp_connection;
740                     break;
741                 default:
742                     break;
743             }
744             break;
745 
746         case HCI_EVENT_COMMAND_STATUS:
747             if (hci_event_command_status_get_command_opcode(packet) == hci_setup_synchronous_connection.opcode) {
748                 if (sco_establishment_active == NULL) break;
749                 status = hci_event_command_status_get_status(packet);
750                 if (status == ERROR_CODE_SUCCESS) break;
751 
752                 hfp_connection = sco_establishment_active;
753                 if (hfp_handle_failed_sco_connection(status)) break;
754                 hfp_connection->establish_audio_connection = 0;
755                 hfp_connection->state = HFP_SERVICE_LEVEL_CONNECTION_ESTABLISHED;
756                 hfp_emit_sco_event(hfp_connection, status, 0, hfp_connection->remote_addr, hfp_connection->negotiated_codec);
757             }
758             break;
759 
760         case HCI_EVENT_SYNCHRONOUS_CONNECTION_COMPLETE:{
761             if (sco_establishment_active == NULL) break;
762             hci_event_synchronous_connection_complete_get_bd_addr(packet, event_addr);
763             hfp_connection = get_hfp_connection_context_for_bd_addr(event_addr, local_role);
764             if (!hfp_connection) {
765                 log_error("HFP: connection does not exist for remote with addr %s.", bd_addr_to_str(event_addr));
766                 return;
767             }
768 
769             status = hci_event_synchronous_connection_complete_get_status(packet);
770             if (status != ERROR_CODE_SUCCESS){
771                 hfp_connection->hf_accept_sco = 0;
772                 if (hfp_handle_failed_sco_connection(status)) break;
773 
774                 hfp_connection->establish_audio_connection = 0;
775                 hfp_connection->state = HFP_SERVICE_LEVEL_CONNECTION_ESTABLISHED;
776                 hfp_emit_sco_event(hfp_connection, status, 0, event_addr, hfp_connection->negotiated_codec);
777                 break;
778             }
779 
780             uint16_t sco_handle = hci_event_synchronous_connection_complete_get_handle(packet);
781             uint8_t  link_type = hci_event_synchronous_connection_complete_get_link_type(packet);
782             uint8_t  transmission_interval = hci_event_synchronous_connection_complete_get_transmission_interval(packet);  // measured in slots
783             uint8_t  retransmission_interval = hci_event_synchronous_connection_complete_get_retransmission_interval(packet);// measured in slots
784             uint16_t rx_packet_length = hci_event_synchronous_connection_complete_get_rx_packet_length(packet); // measured in bytes
785             uint16_t tx_packet_length = hci_event_synchronous_connection_complete_get_tx_packet_length(packet); // measured in bytes
786 
787             switch (link_type){
788                 case 0x00:
789                     log_info("SCO Connection established.");
790                     if (transmission_interval != 0) log_error("SCO Connection: transmission_interval not zero: %d.", transmission_interval);
791                     if (retransmission_interval != 0) log_error("SCO Connection: retransmission_interval not zero: %d.", retransmission_interval);
792                     if (rx_packet_length != 0) log_error("SCO Connection: rx_packet_length not zero: %d.", rx_packet_length);
793                     if (tx_packet_length != 0) log_error("SCO Connection: tx_packet_length not zero: %d.", tx_packet_length);
794                     break;
795                 case 0x02:
796                     log_info("eSCO Connection established. \n");
797                     break;
798                 default:
799                     log_error("(e)SCO reserved link_type 0x%2x", link_type);
800                     break;
801             }
802 
803             log_info("sco_handle 0x%2x, address %s, transmission_interval %u slots, retransmission_interval %u slots, "
804                  " rx_packet_length %u bytes, tx_packet_length %u bytes, air_mode 0x%2x (0x02 == CVSD)\n", sco_handle,
805                  bd_addr_to_str(event_addr), transmission_interval, retransmission_interval, rx_packet_length, tx_packet_length,
806                  hci_event_synchronous_connection_complete_get_air_mode(packet));
807 
808             if (hfp_connection->state == HFP_W4_CONNECTION_ESTABLISHED_TO_SHUTDOWN){
809                 log_info("SCO about to disconnect: HFP_W4_CONNECTION_ESTABLISHED_TO_SHUTDOWN");
810                 hfp_connection->state = HFP_W2_DISCONNECT_SCO;
811                 break;
812             }
813             hfp_connection->sco_handle = sco_handle;
814             hfp_connection->establish_audio_connection = 0;
815             hfp_connection->state = HFP_AUDIO_CONNECTION_ESTABLISHED;
816             hfp_emit_sco_event(hfp_connection, status, sco_handle, event_addr, hfp_connection->negotiated_codec);
817             break;
818         }
819 
820         case HCI_EVENT_DISCONNECTION_COMPLETE:
821             handle = little_endian_read_16(packet,3);
822             hfp_connection = get_hfp_connection_context_for_sco_handle(handle, local_role);
823 
824             if (!hfp_connection) break;
825 
826 #ifdef ENABLE_CC256X_ASSISTED_HFP
827             hfp_connection->cc256x_send_wbs_disassociate = true;
828 #endif
829 #ifdef ENABLE_BCM_PCM_WBS
830             hfp_connection->bcm_send_disable_wbs = true;
831 #endif
832             hfp_connection->sco_handle = HCI_CON_HANDLE_INVALID;
833             hfp_connection->release_audio_connection = 0;
834 
835             if (hfp_connection->state == HFP_W4_SCO_DISCONNECTED_TO_SHUTDOWN){
836                 // RFCOMM already closed -> remote power off
837 #if defined(ENABLE_CC256X_ASSISTED_HFP) || defined (ENABLE_BCM_PCM_WBS)
838                 hfp_connection->state = HFP_W4_WBS_SHUTDOWN;
839 #else
840                 hfp_finalize_connection_context(hfp_connection);
841 #endif
842                 break;
843             }
844 
845             hfp_connection->state = HFP_SERVICE_LEVEL_CONNECTION_ESTABLISHED;
846             hfp_emit_audio_connection_released(hfp_connection, handle);
847 
848             if (hfp_connection->release_slc_connection){
849                 hfp_connection->release_slc_connection = 0;
850                 log_info("SCO disconnected, w2 disconnect RFCOMM\n");
851                 hfp_connection->state = HFP_W2_DISCONNECT_RFCOMM;
852             }
853             break;
854 
855         default:
856             break;
857     }
858 }
859 
860 
861 void hfp_handle_rfcomm_event(uint8_t packet_type, uint16_t channel, uint8_t *packet, uint16_t size, hfp_role_t local_role){
862     UNUSED(packet_type);
863     UNUSED(channel);    // ok: no channel
864     UNUSED(size);
865 
866     bd_addr_t event_addr;
867     uint16_t rfcomm_cid;
868     hfp_connection_t * hfp_connection = NULL;
869     uint8_t status;
870 
871     log_debug("HFP packet_handler type %u, event type %x, size %u", packet_type, hci_event_packet_get_type(packet), size);
872 
873     switch (hci_event_packet_get_type(packet)) {
874 
875         case RFCOMM_EVENT_INCOMING_CONNECTION:
876             // data: event (8), len(8), address(48), channel (8), rfcomm_cid (16)
877             rfcomm_event_incoming_connection_get_bd_addr(packet, event_addr);
878             hfp_connection = provide_hfp_connection_context_for_bd_addr(event_addr, local_role);
879             if (!hfp_connection){
880                 log_info("hfp: no memory to accept incoming connection - decline");
881                 rfcomm_decline_connection(rfcomm_event_incoming_connection_get_rfcomm_cid(packet));
882                 return;
883             }
884             if (hfp_connection->state != HFP_IDLE) {
885                 log_error("hfp: incoming connection but not idle, reject");
886                 rfcomm_decline_connection(rfcomm_event_incoming_connection_get_rfcomm_cid(packet));
887                 return;
888             }
889 
890             hfp_connection->rfcomm_cid = rfcomm_event_incoming_connection_get_rfcomm_cid(packet);
891             hfp_connection->state = HFP_W4_RFCOMM_CONNECTED;
892             rfcomm_accept_connection(hfp_connection->rfcomm_cid);
893             break;
894 
895         case RFCOMM_EVENT_CHANNEL_OPENED:
896             // data: event(8), len(8), status (8), address (48), handle(16), server channel(8), rfcomm_cid(16), max frame size(16)
897 
898             rfcomm_event_channel_opened_get_bd_addr(packet, event_addr);
899             status = rfcomm_event_channel_opened_get_status(packet);
900 
901             hfp_connection = get_hfp_connection_context_for_bd_addr(event_addr, local_role);
902             if (!hfp_connection || (hfp_connection->state != HFP_W4_RFCOMM_CONNECTED)) return;
903 
904             if (status) {
905                 hfp_emit_slc_connection_event(hfp_connection, status, rfcomm_event_channel_opened_get_con_handle(packet), event_addr);
906                 hfp_finalize_connection_context(hfp_connection);
907             } else {
908                 hfp_connection->acl_handle = rfcomm_event_channel_opened_get_con_handle(packet);
909                 hfp_connection->rfcomm_cid = rfcomm_event_channel_opened_get_rfcomm_cid(packet);
910                 bd_addr_copy(hfp_connection->remote_addr, event_addr);
911 
912                 switch (hfp_connection->state){
913                     case HFP_W4_RFCOMM_CONNECTED:
914                         hfp_connection->state = HFP_EXCHANGE_SUPPORTED_FEATURES;
915                         break;
916                     case HFP_W4_CONNECTION_ESTABLISHED_TO_SHUTDOWN:
917                         hfp_connection->state = HFP_W2_DISCONNECT_RFCOMM;
918                         break;
919                     default:
920                         break;
921                 }
922                 rfcomm_request_can_send_now_event(hfp_connection->rfcomm_cid);
923             }
924             break;
925 
926         case RFCOMM_EVENT_CHANNEL_CLOSED:
927             rfcomm_cid = little_endian_read_16(packet,2);
928             hfp_connection = get_hfp_connection_context_for_rfcomm_cid(rfcomm_cid);
929             if (!hfp_connection) break;
930             if (hfp_connection->state == HFP_W4_RFCOMM_DISCONNECTED_AND_RESTART){
931                 hfp_connection->state = HFP_IDLE;
932                 hfp_establish_service_level_connection(hfp_connection->remote_addr, hfp_connection->service_uuid, local_role);
933                 break;
934             }
935             if ( hfp_connection->state == HFP_AUDIO_CONNECTION_ESTABLISHED){
936                 // service connection was released, this implicitly releases audio connection as well
937                 hfp_connection->release_audio_connection = 0;
938                 hci_con_handle_t sco_handle = hfp_connection->sco_handle;
939                 gap_disconnect(hfp_connection->sco_handle);
940                 hfp_connection->state = HFP_W4_SCO_DISCONNECTED_TO_SHUTDOWN;
941                 hfp_emit_audio_connection_released(hfp_connection, sco_handle);
942                 hfp_emit_event(hfp_connection, HFP_SUBEVENT_SERVICE_LEVEL_CONNECTION_RELEASED, 0);
943             } else {
944                 // regular case
945                 hfp_emit_event(hfp_connection, HFP_SUBEVENT_SERVICE_LEVEL_CONNECTION_RELEASED, 0);
946                 hfp_finalize_connection_context(hfp_connection);
947             }
948             break;
949 
950         default:
951             break;
952     }
953 }
954 // translates command string into hfp_command_t CMD
955 
956 typedef struct {
957     const char * command;
958     hfp_command_t command_id;
959 } hfp_command_entry_t;
960 
961 static hfp_command_entry_t hfp_ag_commmand_table[] = {
962     { "AT+BAC=",   HFP_CMD_AVAILABLE_CODECS },
963     { "AT+BCC",    HFP_CMD_TRIGGER_CODEC_CONNECTION_SETUP },
964     { "AT+BCS=",   HFP_CMD_HF_CONFIRMED_CODEC },
965     { "AT+BIA=",   HFP_CMD_ENABLE_INDIVIDUAL_AG_INDICATOR_STATUS_UPDATE, }, // +BIA:<enabled>,,<enabled>,,,<enabled>
966     { "AT+BIEV=",  HFP_CMD_HF_INDICATOR_STATUS },
967     { "AT+BIND=",  HFP_CMD_LIST_GENERIC_STATUS_INDICATORS },
968     { "AT+BIND=?", HFP_CMD_RETRIEVE_GENERIC_STATUS_INDICATORS },
969     { "AT+BIND?",  HFP_CMD_RETRIEVE_GENERIC_STATUS_INDICATORS_STATE },
970     { "AT+BINP",   HFP_CMD_HF_REQUEST_PHONE_NUMBER },
971     { "AT+BLDN",   HFP_CMD_REDIAL_LAST_NUMBER },
972     { "AT+BRSF=",  HFP_CMD_SUPPORTED_FEATURES },
973     { "AT+BTRH=",  HFP_CMD_RESPONSE_AND_HOLD_COMMAND },
974     { "AT+BTRH?",  HFP_CMD_RESPONSE_AND_HOLD_QUERY },
975     { "AT+BVRA=",  HFP_CMD_AG_ACTIVATE_VOICE_RECOGNITION },
976     { "AT+CCWA=",  HFP_CMD_ENABLE_CALL_WAITING_NOTIFICATION},
977     { "AT+CHLD=",  HFP_CMD_CALL_HOLD },
978     { "AT+CHLD=?", HFP_CMD_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES },
979     { "AT+CHUP",   HFP_CMD_HANG_UP_CALL },
980     { "AT+CIND=?", HFP_CMD_RETRIEVE_AG_INDICATORS },
981     { "AT+CIND?",  HFP_CMD_RETRIEVE_AG_INDICATORS_STATUS },
982     { "AT+CLCC",   HFP_CMD_LIST_CURRENT_CALLS },
983     { "AT+CLIP=",  HFP_CMD_ENABLE_CLIP},
984     { "AT+CMEE=",  HFP_CMD_ENABLE_EXTENDED_AUDIO_GATEWAY_ERROR},
985     { "AT+CMER=",  HFP_CMD_ENABLE_INDICATOR_STATUS_UPDATE },
986     { "AT+CNUM",   HFP_CMD_GET_SUBSCRIBER_NUMBER_INFORMATION },
987     { "AT+COPS=",  HFP_CMD_QUERY_OPERATOR_SELECTION_NAME_FORMAT },
988     { "AT+COPS?",  HFP_CMD_QUERY_OPERATOR_SELECTION_NAME },
989     { "AT+NREC=",  HFP_CMD_TURN_OFF_EC_AND_NR, },
990     { "AT+VGM=",   HFP_CMD_SET_MICROPHONE_GAIN },
991     { "AT+VGS=",   HFP_CMD_SET_SPEAKER_GAIN },
992     { "AT+VTS:",   HFP_CMD_TRANSMIT_DTMF_CODES },
993     { "ATA",       HFP_CMD_CALL_ANSWERED },
994 };
995 
996 static hfp_command_entry_t hfp_hf_commmand_table[] = {
997     { "+BCS:",  HFP_CMD_AG_SUGGESTED_CODEC },
998     { "+BIND:", HFP_CMD_SET_GENERIC_STATUS_INDICATOR_STATUS },
999     { "+BINP",  HFP_CMD_AG_SENT_PHONE_NUMBER },
1000     { "+BRSF:", HFP_CMD_SUPPORTED_FEATURES },
1001     { "+BSIR:", HFP_CMD_CHANGE_IN_BAND_RING_TONE_SETTING },
1002     { "+BTRH:", HFP_CMD_RESPONSE_AND_HOLD_STATUS },
1003     { "+BVRA:", HFP_CMD_AG_ACTIVATE_VOICE_RECOGNITION },
1004     { "+CCWA:", HFP_CMD_AG_SENT_CALL_WAITING_NOTIFICATION_UPDATE, },
1005     { "+CHLD:", HFP_CMD_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES },
1006     { "+CIEV:", HFP_CMD_TRANSFER_AG_INDICATOR_STATUS},
1007     { "+CIND:", HFP_CMD_RETRIEVE_AG_INDICATORS_GENERIC },
1008     { "+CLCC:", HFP_CMD_LIST_CURRENT_CALLS },
1009     { "+CLIP:", HFP_CMD_AG_SENT_CLIP_INFORMATION },
1010     { "+CME ERROR:", HFP_CMD_EXTENDED_AUDIO_GATEWAY_ERROR },
1011     { "+CNUM:", HFP_CMD_GET_SUBSCRIBER_NUMBER_INFORMATION},
1012     { "+COPS:", HFP_CMD_QUERY_OPERATOR_SELECTION_NAME },
1013     { "+VGM:",  HFP_CMD_SET_MICROPHONE_GAIN },
1014     { "+VGS:",  HFP_CMD_SET_SPEAKER_GAIN},
1015     { "ERROR",  HFP_CMD_ERROR},
1016     { "NOP",    HFP_CMD_NONE}, // dummy command used by unit tests
1017     { "OK",     HFP_CMD_OK },
1018     { "RING",   HFP_CMD_RING },
1019 };
1020 
1021 static hfp_command_t parse_command(const char * line_buffer, int isHandsFree){
1022 
1023     // table lookup based on role
1024     uint16_t num_entries;
1025     hfp_command_entry_t * table;
1026     if (isHandsFree == 0){
1027         table = hfp_ag_commmand_table;
1028         num_entries = sizeof(hfp_ag_commmand_table) / sizeof(hfp_command_entry_t);
1029     } else {
1030         table = hfp_hf_commmand_table;
1031         num_entries = sizeof(hfp_hf_commmand_table) / sizeof(hfp_command_entry_t);
1032     }
1033     // binary search
1034     uint16_t left = 0;
1035     uint16_t right = num_entries - 1;
1036     while (left <= right){
1037         uint16_t middle = left + (right - left) / 2;
1038         hfp_command_entry_t *entry = &table[middle];
1039         int match = strcmp(line_buffer, entry->command);
1040         if (match < 0){
1041             // search term is lower than middle element
1042             if (right == 0) break;
1043             right = middle - 1;
1044         } else if (match == 0){
1045             return entry->command_id;
1046         } else {
1047             // search term is higher than middle element
1048             left = middle + 1;
1049         }
1050     }
1051 
1052     // note: if parser in CMD_HEADER state would treats digits and maybe '+' as separator, match on "ATD" would work.
1053     // note: phone number is currently expected in line_buffer[3..]
1054     // prefix match on 'ATD', AG only
1055     if ((isHandsFree == 0) && (strncmp(line_buffer, HFP_CALL_PHONE_NUMBER, strlen(HFP_CALL_PHONE_NUMBER)) == 0)){
1056         return HFP_CMD_CALL_PHONE_NUMBER;
1057     }
1058 
1059     // Valid looking, but unknown commands/responses
1060     if ((isHandsFree == 0) && (strncmp(line_buffer, "AT+", 3) == 0)){
1061         return HFP_CMD_UNKNOWN;
1062     }
1063 
1064     if ((isHandsFree != 0) && (strncmp(line_buffer, "+", 1) == 0)){
1065         return HFP_CMD_UNKNOWN;
1066     }
1067 
1068     return HFP_CMD_NONE;
1069 }
1070 
1071 static void hfp_parser_store_byte(hfp_connection_t * hfp_connection, uint8_t byte){
1072     if ((hfp_connection->line_size + 1 ) >= HFP_MAX_INDICATOR_DESC_SIZE) return;
1073     hfp_connection->line_buffer[hfp_connection->line_size++] = byte;
1074     hfp_connection->line_buffer[hfp_connection->line_size] = 0;
1075 }
1076 static int hfp_parser_is_buffer_empty(hfp_connection_t * hfp_connection){
1077     return hfp_connection->line_size == 0;
1078 }
1079 
1080 static int hfp_parser_is_end_of_line(uint8_t byte){
1081     return (byte == '\n') || (byte == '\r');
1082 }
1083 
1084 static void hfp_parser_reset_line_buffer(hfp_connection_t *hfp_connection) {
1085     hfp_connection->line_size = 0;
1086 }
1087 
1088 static void hfp_parser_store_if_token(hfp_connection_t * hfp_connection, uint8_t byte){
1089     switch (byte){
1090         case ',':
1091 		case '-':
1092         case ';':
1093         case '(':
1094         case ')':
1095         case '\n':
1096         case '\r':
1097             break;
1098         default:
1099             hfp_parser_store_byte(hfp_connection, byte);
1100             break;
1101     }
1102 }
1103 
1104 static bool hfp_parser_is_separator( uint8_t byte){
1105     switch (byte){
1106         case ',':
1107 		case '-':
1108         case ';':
1109         case '\n':
1110         case '\r':
1111             return true;
1112         default:
1113             return false;
1114     }
1115 }
1116 
1117 static bool hfp_parse_byte(hfp_connection_t * hfp_connection, uint8_t byte, int isHandsFree){
1118 
1119     // handle doubles quotes
1120     if (byte == '"'){
1121         hfp_connection->parser_quoted = !hfp_connection->parser_quoted;
1122         return true;
1123     }
1124     if (hfp_connection->parser_quoted) {
1125         hfp_parser_store_byte(hfp_connection, byte);
1126         return true;
1127     }
1128 
1129     // ignore spaces outside command or double quotes (required e.g. for '+CME ERROR:..") command
1130     if ((byte == ' ') && (hfp_connection->parser_state != HFP_PARSER_CMD_HEADER)) return true;
1131 
1132     bool processed = true;
1133 
1134     switch (hfp_connection->parser_state) {
1135         case HFP_PARSER_CMD_HEADER:
1136             switch (byte) {
1137                 case '\n':
1138                 case '\r':
1139                 case ';':
1140                     // ignore separator
1141                     break;
1142                 case ':':
1143                 case '?':
1144                     // store separator
1145                     hfp_parser_store_byte(hfp_connection, byte);
1146                     break;
1147                 case '=':
1148                     // equal sign: remember and wait for next char to decided between '=?' and '=\?'
1149                     hfp_connection->found_equal_sign = true;
1150                     hfp_parser_store_byte(hfp_connection, byte);
1151                     return true;
1152                 default:
1153                     // store if not lookahead
1154                     if (!hfp_connection->found_equal_sign) {
1155                         hfp_parser_store_byte(hfp_connection, byte);
1156                         return true;
1157                     }
1158                     // mark as lookahead
1159                     processed = false;
1160                     break;
1161             }
1162 
1163             // ignore empty tokens
1164             if (hfp_parser_is_buffer_empty(hfp_connection)) return true;
1165 
1166             // parse
1167             hfp_connection->command = parse_command((char *)hfp_connection->line_buffer, isHandsFree);
1168 
1169             // pick +CIND version based on connection state: descriptions during SLC vs. states later
1170             if (hfp_connection->command == HFP_CMD_RETRIEVE_AG_INDICATORS_GENERIC){
1171                 switch(hfp_connection->state){
1172                     case HFP_W4_RETRIEVE_INDICATORS_STATUS:
1173                         hfp_connection->command = HFP_CMD_RETRIEVE_AG_INDICATORS_STATUS;
1174                         break;
1175                     case HFP_W4_RETRIEVE_INDICATORS:
1176                         hfp_connection->command = HFP_CMD_RETRIEVE_AG_INDICATORS;
1177                         break;
1178                     default:
1179                         hfp_connection->command = HFP_CMD_UNKNOWN;
1180                         break;
1181                 }
1182             }
1183 
1184             log_info("command string '%s', handsfree %u -> cmd id %u", (char *)hfp_connection->line_buffer, isHandsFree, hfp_connection->command);
1185 
1186             // next state
1187             hfp_connection->found_equal_sign = false;
1188             hfp_parser_reset_line_buffer(hfp_connection);
1189             hfp_connection->parser_state = HFP_PARSER_CMD_SEQUENCE;
1190 
1191             return processed;
1192 
1193         case HFP_PARSER_CMD_SEQUENCE:
1194             // handle empty fields
1195             if ((byte == ',' ) && (hfp_connection->line_size == 0)){
1196                 hfp_connection->line_buffer[0] = 0;
1197                 hfp_connection->ignore_value = 1;
1198                 parse_sequence(hfp_connection);
1199                 return true;
1200             }
1201 
1202             hfp_parser_store_if_token(hfp_connection, byte);
1203             if (!hfp_parser_is_separator(byte)) return true;
1204 
1205             // ignore empty tokens
1206             if (hfp_parser_is_buffer_empty(hfp_connection) && (hfp_connection->ignore_value == 0)) return true;
1207 
1208             parse_sequence(hfp_connection);
1209 
1210             hfp_parser_reset_line_buffer(hfp_connection);
1211 
1212             switch (hfp_connection->command){
1213                 case HFP_CMD_AG_SENT_PHONE_NUMBER:
1214                 case HFP_CMD_AG_SENT_CALL_WAITING_NOTIFICATION_UPDATE:
1215                 case HFP_CMD_AG_SENT_CLIP_INFORMATION:
1216                 case HFP_CMD_TRANSFER_AG_INDICATOR_STATUS:
1217                 case HFP_CMD_QUERY_OPERATOR_SELECTION_NAME:
1218                 case HFP_CMD_QUERY_OPERATOR_SELECTION_NAME_FORMAT:
1219                 case HFP_CMD_RETRIEVE_AG_INDICATORS:
1220                 case HFP_CMD_RETRIEVE_GENERIC_STATUS_INDICATORS_STATE:
1221                 case HFP_CMD_HF_INDICATOR_STATUS:
1222                     hfp_connection->parser_state = HFP_PARSER_SECOND_ITEM;
1223                     break;
1224                 default:
1225                     break;
1226             }
1227             return true;
1228 
1229         case HFP_PARSER_SECOND_ITEM:
1230 
1231             hfp_parser_store_if_token(hfp_connection, byte);
1232             if (!hfp_parser_is_separator(byte)) return true;
1233 
1234             switch (hfp_connection->command){
1235                 case HFP_CMD_QUERY_OPERATOR_SELECTION_NAME:
1236                     log_info("format %s, ", hfp_connection->line_buffer);
1237                     hfp_connection->network_operator.format =  btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1238                     break;
1239                 case HFP_CMD_QUERY_OPERATOR_SELECTION_NAME_FORMAT:
1240                     log_info("format %s \n", hfp_connection->line_buffer);
1241                     hfp_connection->network_operator.format =  btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1242                     break;
1243                 case HFP_CMD_LIST_GENERIC_STATUS_INDICATORS:
1244                 case HFP_CMD_RETRIEVE_GENERIC_STATUS_INDICATORS:
1245                 case HFP_CMD_RETRIEVE_GENERIC_STATUS_INDICATORS_STATE:
1246                     hfp_connection->generic_status_indicators[hfp_connection->parser_item_index].state = (uint8_t)btstack_atoi((char*)hfp_connection->line_buffer);
1247                     break;
1248                 case HFP_CMD_TRANSFER_AG_INDICATOR_STATUS:
1249                     hfp_connection->ag_indicators[hfp_connection->parser_item_index].status = (uint8_t)btstack_atoi((char*)hfp_connection->line_buffer);
1250                     log_info("%d \n", hfp_connection->ag_indicators[hfp_connection->parser_item_index].status);
1251                     hfp_connection->ag_indicators[hfp_connection->parser_item_index].status_changed = 1;
1252                     break;
1253                 case HFP_CMD_RETRIEVE_AG_INDICATORS:
1254                     hfp_connection->ag_indicators[hfp_connection->parser_item_index].min_range = btstack_atoi((char *)hfp_connection->line_buffer);
1255                     log_info("%s, ", hfp_connection->line_buffer);
1256                     break;
1257                 case HFP_CMD_AG_SENT_PHONE_NUMBER:
1258                 case HFP_CMD_AG_SENT_CALL_WAITING_NOTIFICATION_UPDATE:
1259                 case HFP_CMD_AG_SENT_CLIP_INFORMATION:
1260                     hfp_connection->bnip_type = (uint8_t)btstack_atoi((char*)hfp_connection->line_buffer);
1261                     break;
1262                 case HFP_CMD_HF_INDICATOR_STATUS:
1263                     hfp_connection->parser_indicator_value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1264                     break;
1265                 default:
1266                     break;
1267             }
1268 
1269             hfp_parser_reset_line_buffer(hfp_connection);
1270 
1271             hfp_connection->parser_state = HFP_PARSER_THIRD_ITEM;
1272 
1273             return true;
1274 
1275         case HFP_PARSER_THIRD_ITEM:
1276 
1277             hfp_parser_store_if_token(hfp_connection, byte);
1278             if (!hfp_parser_is_separator(byte)) return true;
1279 
1280             switch (hfp_connection->command){
1281                 case HFP_CMD_QUERY_OPERATOR_SELECTION_NAME:
1282                     strncpy(hfp_connection->network_operator.name, (char *)hfp_connection->line_buffer, HFP_MAX_NETWORK_OPERATOR_NAME_SIZE);
1283                     hfp_connection->network_operator.name[HFP_MAX_NETWORK_OPERATOR_NAME_SIZE - 1] = 0;
1284                     log_info("name %s\n", hfp_connection->line_buffer);
1285                     break;
1286                 case HFP_CMD_RETRIEVE_AG_INDICATORS:
1287                     hfp_connection->ag_indicators[hfp_connection->parser_item_index].max_range = btstack_atoi((char *)hfp_connection->line_buffer);
1288                     hfp_next_indicators_index(hfp_connection);
1289                     hfp_connection->ag_indicators_nr = hfp_connection->parser_item_index;
1290                     log_info("%s)\n", hfp_connection->line_buffer);
1291                     break;
1292                 default:
1293                     break;
1294             }
1295 
1296             hfp_parser_reset_line_buffer(hfp_connection);
1297 
1298             if (hfp_connection->command == HFP_CMD_RETRIEVE_AG_INDICATORS){
1299                 hfp_connection->parser_state = HFP_PARSER_CMD_SEQUENCE;
1300             } else {
1301                 hfp_connection->parser_state = HFP_PARSER_CMD_HEADER;
1302             }
1303             return true;
1304 
1305         default:
1306             btstack_assert(false);
1307             return true;
1308     }
1309 }
1310 
1311 void hfp_parse(hfp_connection_t * hfp_connection, uint8_t byte, int isHandsFree){
1312     bool processed = false;
1313     while (!processed){
1314         processed = hfp_parse_byte(hfp_connection, byte, isHandsFree);
1315     }
1316     // reset parser state on end-of-line
1317     if (hfp_parser_is_end_of_line(byte)){
1318         hfp_connection->parser_item_index = 0;
1319         hfp_connection->parser_state = HFP_PARSER_CMD_HEADER;
1320     }
1321 }
1322 
1323 static void parse_sequence(hfp_connection_t * hfp_connection){
1324     int value;
1325     switch (hfp_connection->command){
1326         case HFP_CMD_SET_GENERIC_STATUS_INDICATOR_STATUS:
1327             value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1328             int i;
1329             switch (hfp_connection->parser_item_index){
1330                 case 0:
1331                     for (i=0;i<hfp_connection->generic_status_indicators_nr;i++){
1332                         if (hfp_connection->generic_status_indicators[i].uuid == value){
1333                             hfp_connection->parser_indicator_index = i;
1334                             break;
1335                         }
1336                     }
1337                     break;
1338                 case 1:
1339                     if (hfp_connection->parser_indicator_index <0) break;
1340                     hfp_connection->generic_status_indicators[hfp_connection->parser_indicator_index].state = value;
1341                     log_info("HFP_CMD_SET_GENERIC_STATUS_INDICATOR_STATUS set indicator at index %u, to %u\n",
1342                      hfp_connection->parser_item_index, value);
1343                     break;
1344                 default:
1345                     break;
1346             }
1347             hfp_next_indicators_index(hfp_connection);
1348             break;
1349 
1350         case HFP_CMD_GET_SUBSCRIBER_NUMBER_INFORMATION:
1351             switch(hfp_connection->parser_item_index){
1352                 case 0:
1353                     strncpy(hfp_connection->bnip_number, (char *)hfp_connection->line_buffer, sizeof(hfp_connection->bnip_number));
1354                     hfp_connection->bnip_number[sizeof(hfp_connection->bnip_number)-1] = 0;
1355                     break;
1356                 case 1:
1357                     value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1358                     hfp_connection->bnip_type = value;
1359                     break;
1360                 default:
1361                     break;
1362             }
1363             // index > 2 are ignored in switch above
1364             hfp_connection->parser_item_index++;
1365             break;
1366         case HFP_CMD_LIST_CURRENT_CALLS:
1367             switch(hfp_connection->parser_item_index){
1368                 case 0:
1369                     value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1370                     hfp_connection->clcc_idx = value;
1371                     break;
1372                 case 1:
1373                     value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1374                     hfp_connection->clcc_dir = value;
1375                     break;
1376                 case 2:
1377                     value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1378                     hfp_connection->clcc_status = value;
1379                     break;
1380                 case 3:
1381                     value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1382                     hfp_connection->clcc_mode = value;
1383                     break;
1384                 case 4:
1385                     value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1386                     hfp_connection->clcc_mpty = value;
1387                     break;
1388                 case 5:
1389                     strncpy(hfp_connection->bnip_number, (char *)hfp_connection->line_buffer, sizeof(hfp_connection->bnip_number));
1390                     hfp_connection->bnip_number[sizeof(hfp_connection->bnip_number)-1] = 0;
1391                     break;
1392                 case 6:
1393                     value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1394                     hfp_connection->bnip_type = value;
1395                     break;
1396                 default:
1397                     break;
1398             }
1399             // index > 6 are ignored in switch above
1400             hfp_connection->parser_item_index++;
1401             break;
1402         case HFP_CMD_SET_MICROPHONE_GAIN:
1403             value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1404             hfp_connection->microphone_gain = value;
1405             log_info("hfp parse HFP_CMD_SET_MICROPHONE_GAIN %d\n", value);
1406             break;
1407         case HFP_CMD_SET_SPEAKER_GAIN:
1408             value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1409             hfp_connection->speaker_gain = value;
1410             log_info("hfp parse HFP_CMD_SET_SPEAKER_GAIN %d\n", value);
1411             break;
1412         case HFP_CMD_HF_ACTIVATE_VOICE_RECOGNITION:
1413             value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1414             hfp_connection->ag_activate_voice_recognition = value;
1415             log_info("hfp parse HFP_CMD_HF_ACTIVATE_VOICE_RECOGNITION %d\n", value);
1416             break;
1417         case HFP_CMD_TURN_OFF_EC_AND_NR:
1418             value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1419             hfp_connection->ag_echo_and_noise_reduction = value;
1420             log_info("hfp parse HFP_CMD_TURN_OFF_EC_AND_NR %d\n", value);
1421             break;
1422         case HFP_CMD_CHANGE_IN_BAND_RING_TONE_SETTING:
1423             value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1424             hfp_connection->remote_supported_features = store_bit(hfp_connection->remote_supported_features, HFP_AGSF_IN_BAND_RING_TONE, value);
1425             log_info("hfp parse HFP_CHANGE_IN_BAND_RING_TONE_SETTING %d\n", value);
1426             break;
1427         case HFP_CMD_HF_CONFIRMED_CODEC:
1428             hfp_connection->codec_confirmed = btstack_atoi((char*)hfp_connection->line_buffer);
1429             log_info("hfp parse HFP_CMD_HF_CONFIRMED_CODEC %d\n", hfp_connection->codec_confirmed);
1430             break;
1431         case HFP_CMD_AG_SUGGESTED_CODEC:
1432             hfp_connection->suggested_codec = btstack_atoi((char*)hfp_connection->line_buffer);
1433             log_info("hfp parse HFP_CMD_AG_SUGGESTED_CODEC %d\n", hfp_connection->suggested_codec);
1434             break;
1435         case HFP_CMD_SUPPORTED_FEATURES:
1436             hfp_connection->remote_supported_features = btstack_atoi((char*)hfp_connection->line_buffer);
1437             log_info("Parsed supported feature %d\n", (int) hfp_connection->remote_supported_features);
1438             break;
1439         case HFP_CMD_AVAILABLE_CODECS:
1440             log_info("Parsed codec %s\n", hfp_connection->line_buffer);
1441             hfp_connection->remote_codecs[hfp_connection->parser_item_index] = (uint16_t)btstack_atoi((char*)hfp_connection->line_buffer);
1442             hfp_next_codec_index(hfp_connection);
1443             hfp_connection->remote_codecs_nr = hfp_connection->parser_item_index;
1444             break;
1445         case HFP_CMD_RETRIEVE_AG_INDICATORS:
1446             strncpy((char *)hfp_connection->ag_indicators[hfp_connection->parser_item_index].name,  (char *)hfp_connection->line_buffer, HFP_MAX_INDICATOR_DESC_SIZE);
1447             hfp_connection->ag_indicators[hfp_connection->parser_item_index].name[HFP_MAX_INDICATOR_DESC_SIZE-1] = 0;
1448             hfp_connection->ag_indicators[hfp_connection->parser_item_index].index = hfp_connection->parser_item_index+1;
1449             log_info("Indicator %d: %s (", hfp_connection->ag_indicators_nr+1, hfp_connection->line_buffer);
1450             break;
1451         case HFP_CMD_RETRIEVE_AG_INDICATORS_STATUS:
1452             log_info("Parsed Indicator %d with status: %s\n", hfp_connection->parser_item_index+1, hfp_connection->line_buffer);
1453             hfp_connection->ag_indicators[hfp_connection->parser_item_index].status = btstack_atoi((char *) hfp_connection->line_buffer);
1454             hfp_next_indicators_index(hfp_connection);
1455             break;
1456         case HFP_CMD_ENABLE_INDICATOR_STATUS_UPDATE:
1457             hfp_next_indicators_index(hfp_connection);
1458             if (hfp_connection->parser_item_index != 4) break;
1459             log_info("Parsed Enable indicators: %s\n", hfp_connection->line_buffer);
1460             value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1461             hfp_connection->enable_status_update_for_ag_indicators = (uint8_t) value;
1462             break;
1463         case HFP_CMD_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES:
1464             log_info("Parsed Support call hold: %s\n", hfp_connection->line_buffer);
1465             if (hfp_connection->line_size > 2 ) break;
1466             memcpy((char *)hfp_connection->remote_call_services[hfp_connection->remote_call_services_index].name, (char *)hfp_connection->line_buffer, HFP_CALL_SERVICE_SIZE-1);
1467             hfp_connection->remote_call_services[hfp_connection->remote_call_services_index].name[HFP_CALL_SERVICE_SIZE - 1] = 0;
1468             hfp_next_remote_call_services_index(hfp_connection);
1469             break;
1470         case HFP_CMD_LIST_GENERIC_STATUS_INDICATORS:
1471         case HFP_CMD_RETRIEVE_GENERIC_STATUS_INDICATORS:
1472             log_info("Parsed Generic status indicator: %s\n", hfp_connection->line_buffer);
1473             hfp_connection->generic_status_indicators[hfp_connection->parser_item_index].uuid = (uint16_t)btstack_atoi((char*)hfp_connection->line_buffer);
1474             hfp_next_indicators_index(hfp_connection);
1475             hfp_connection->generic_status_indicators_nr = hfp_connection->parser_item_index;
1476             break;
1477         case HFP_CMD_RETRIEVE_GENERIC_STATUS_INDICATORS_STATE:
1478             // HF parses inital AG gen. ind. state
1479             log_info("Parsed List generic status indicator %s state: ", hfp_connection->line_buffer);
1480             hfp_connection->parser_item_index = hfp_parse_indicator_index(hfp_connection);
1481             break;
1482         case HFP_CMD_HF_INDICATOR_STATUS:
1483             hfp_connection->parser_indicator_index = hfp_parse_indicator_index(hfp_connection);
1484             log_info("Parsed HF indicator index %u", hfp_connection->parser_indicator_index);
1485             break;
1486         case HFP_CMD_ENABLE_INDIVIDUAL_AG_INDICATOR_STATUS_UPDATE:
1487             // AG parses new gen. ind. state
1488             if (hfp_connection->ignore_value){
1489                 hfp_connection->ignore_value = 0;
1490                 log_info("Parsed Enable AG indicator pos %u('%s') - unchanged (stays %u)\n", hfp_connection->parser_item_index,
1491                     hfp_connection->ag_indicators[hfp_connection->parser_item_index].name, hfp_connection->ag_indicators[hfp_connection->parser_item_index].enabled);
1492             }
1493             else if (hfp_connection->ag_indicators[hfp_connection->parser_item_index].mandatory){
1494                 log_info("Parsed Enable AG indicator pos %u('%s') - ignore (mandatory)\n",
1495                     hfp_connection->parser_item_index, hfp_connection->ag_indicators[hfp_connection->parser_item_index].name);
1496             } else {
1497                 value = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1498                 hfp_connection->ag_indicators[hfp_connection->parser_item_index].enabled = value;
1499                 log_info("Parsed Enable AG indicator pos %u('%s'): %u\n", hfp_connection->parser_item_index,
1500                     hfp_connection->ag_indicators[hfp_connection->parser_item_index].name, value);
1501             }
1502             hfp_next_indicators_index(hfp_connection);
1503             break;
1504         case HFP_CMD_TRANSFER_AG_INDICATOR_STATUS:
1505             // indicators are indexed starting with 1
1506             hfp_connection->parser_item_index = hfp_parse_indicator_index(hfp_connection);
1507             log_info("Parsed status of the AG indicator %d, status ", hfp_connection->parser_item_index);
1508             break;
1509         case HFP_CMD_QUERY_OPERATOR_SELECTION_NAME:
1510             hfp_connection->network_operator.mode = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1511             log_info("Parsed network operator mode: %d, ", hfp_connection->network_operator.mode);
1512             break;
1513         case HFP_CMD_QUERY_OPERATOR_SELECTION_NAME_FORMAT:
1514             if (hfp_connection->line_buffer[0] == '3'){
1515                 log_info("Parsed Set network operator format : %s, ", hfp_connection->line_buffer);
1516                 break;
1517             }
1518             // TODO emit ERROR, wrong format
1519             log_info("ERROR Set network operator format: index %s not supported\n", hfp_connection->line_buffer);
1520             break;
1521         case HFP_CMD_ERROR:
1522             break;
1523         case HFP_CMD_EXTENDED_AUDIO_GATEWAY_ERROR:
1524             hfp_connection->extended_audio_gateway_error = 1;
1525             hfp_connection->extended_audio_gateway_error_value = (uint8_t)btstack_atoi((char*)hfp_connection->line_buffer);
1526             break;
1527         case HFP_CMD_ENABLE_EXTENDED_AUDIO_GATEWAY_ERROR:
1528             hfp_connection->enable_extended_audio_gateway_error_report = (uint8_t)btstack_atoi((char*)hfp_connection->line_buffer);
1529             hfp_connection->ok_pending = 1;
1530             hfp_connection->extended_audio_gateway_error = 0;
1531             break;
1532         case HFP_CMD_AG_SENT_PHONE_NUMBER:
1533         case HFP_CMD_AG_SENT_CALL_WAITING_NOTIFICATION_UPDATE:
1534         case HFP_CMD_AG_SENT_CLIP_INFORMATION:
1535             strncpy(hfp_connection->bnip_number, (char *)hfp_connection->line_buffer, sizeof(hfp_connection->bnip_number));
1536             hfp_connection->bnip_number[sizeof(hfp_connection->bnip_number)-1] = 0;
1537             break;
1538         case HFP_CMD_CALL_HOLD:
1539             hfp_connection->ag_call_hold_action = hfp_connection->line_buffer[0] - '0';
1540             if (hfp_connection->line_buffer[1] != '\0'){
1541                 hfp_connection->call_index = btstack_atoi((char *)&hfp_connection->line_buffer[1]);
1542             }
1543             break;
1544         case HFP_CMD_RESPONSE_AND_HOLD_COMMAND:
1545             hfp_connection->ag_response_and_hold_action = btstack_atoi((char *)&hfp_connection->line_buffer[0]);
1546             break;
1547         case HFP_CMD_TRANSMIT_DTMF_CODES:
1548             hfp_connection->ag_dtmf_code = hfp_connection->line_buffer[0];
1549             break;
1550         case HFP_CMD_ENABLE_CLIP:
1551             hfp_connection->clip_enabled = hfp_connection->line_buffer[0] != '0';
1552             break;
1553         case HFP_CMD_ENABLE_CALL_WAITING_NOTIFICATION:
1554             hfp_connection->call_waiting_notification_enabled = hfp_connection->line_buffer[0] != '0';
1555             break;
1556         default:
1557             break;
1558     }
1559 }
1560 
1561 static void hfp_handle_start_sdp_client_query(void * context){
1562     UNUSED(context);
1563 
1564     btstack_linked_list_iterator_t it;
1565     btstack_linked_list_iterator_init(&it, &hfp_connections);
1566     while (btstack_linked_list_iterator_has_next(&it)){
1567         hfp_connection_t * connection = (hfp_connection_t *)btstack_linked_list_iterator_next(&it);
1568 
1569         if (connection->state != HFP_W2_SEND_SDP_QUERY) continue;
1570 
1571         connection->state = HFP_W4_SDP_QUERY_COMPLETE;
1572         sdp_query_context.local_role = connection->local_role;
1573         (void)memcpy(sdp_query_context.remote_address, connection->remote_addr, 6);
1574         sdp_client_query_rfcomm_channel_and_name_for_service_class_uuid(&handle_query_rfcomm_event, connection->remote_addr, connection->service_uuid);
1575         return;
1576     }
1577 }
1578 
1579 void hfp_establish_service_level_connection(bd_addr_t bd_addr, uint16_t service_uuid, hfp_role_t local_role){
1580     hfp_connection_t * hfp_connection = provide_hfp_connection_context_for_bd_addr(bd_addr, local_role);
1581     log_info("hfp_connect %s, hfp_connection %p", bd_addr_to_str(bd_addr), hfp_connection);
1582 
1583     if (!hfp_connection) {
1584         log_error("hfp_establish_service_level_connection for addr %s failed", bd_addr_to_str(bd_addr));
1585         return;
1586     }
1587     switch (hfp_connection->state){
1588         case HFP_W2_DISCONNECT_RFCOMM:
1589             hfp_connection->state = HFP_SERVICE_LEVEL_CONNECTION_ESTABLISHED;
1590             return;
1591         case HFP_W4_RFCOMM_DISCONNECTED:
1592             hfp_connection->state = HFP_W4_RFCOMM_DISCONNECTED_AND_RESTART;
1593             return;
1594         case HFP_IDLE:
1595             (void)memcpy(hfp_connection->remote_addr, bd_addr, 6);
1596             hfp_connection->state = HFP_W2_SEND_SDP_QUERY;
1597             hfp_connection->service_uuid = service_uuid;
1598 
1599             hfp_handle_sdp_client_query_request.callback = &hfp_handle_start_sdp_client_query;
1600             // ignore ERROR_CODE_COMMAND_DISALLOWED because in that case, we already have requested an SDP callback
1601             (void) sdp_client_register_query_callback(&hfp_handle_sdp_client_query_request);
1602             break;
1603         default:
1604             break;
1605     }
1606 }
1607 
1608 void hfp_release_service_level_connection(hfp_connection_t * hfp_connection){
1609     if (!hfp_connection) return;
1610     hfp_release_audio_connection(hfp_connection);
1611 
1612     if (hfp_connection->state < HFP_W4_RFCOMM_CONNECTED){
1613         hfp_connection->state = HFP_IDLE;
1614         return;
1615     }
1616 
1617     if (hfp_connection->state == HFP_W4_RFCOMM_CONNECTED){
1618         hfp_connection->state = HFP_W4_CONNECTION_ESTABLISHED_TO_SHUTDOWN;
1619         return;
1620     }
1621 
1622     if (hfp_connection->state < HFP_W4_SCO_CONNECTED){
1623         hfp_connection->state = HFP_W2_DISCONNECT_RFCOMM;
1624         return;
1625     }
1626 
1627     if (hfp_connection->state < HFP_W4_SCO_DISCONNECTED){
1628         hfp_connection->state = HFP_W2_DISCONNECT_SCO;
1629         return;
1630     }
1631 
1632     // HFP_W4_SCO_DISCONNECTED or later
1633     hfp_connection->release_slc_connection = 1;
1634 }
1635 
1636 void hfp_release_audio_connection(hfp_connection_t * hfp_connection){
1637     if (!hfp_connection) return;
1638     if (hfp_connection->state >= HFP_W2_DISCONNECT_SCO) return;
1639     hfp_connection->release_audio_connection = 1;
1640 }
1641 
1642 static const struct link_settings {
1643     const uint16_t max_latency;
1644     const uint8_t  retransmission_effort;
1645     const uint16_t packet_types;
1646     const bool     eSCO;
1647     const uint8_t  codec;
1648 } hfp_link_settings [] = {
1649     { 0xffff, 0xff, SCO_PACKET_TYPES_HV1,  false, HFP_CODEC_CVSD }, // HFP_LINK_SETTINGS_D0
1650     { 0xffff, 0xff, SCO_PACKET_TYPES_HV3,  false, HFP_CODEC_CVSD }, // HFP_LINK_SETTINGS_D1
1651     { 0x0007, 0x01, SCO_PACKET_TYPES_EV3,  true,  HFP_CODEC_CVSD }, // HFP_LINK_SETTINGS_S1
1652     { 0x0007, 0x01, SCO_PACKET_TYPES_2EV3, true,  HFP_CODEC_CVSD }, // HFP_LINK_SETTINGS_S2
1653     { 0x000a, 0x01, SCO_PACKET_TYPES_2EV3, true,  HFP_CODEC_CVSD }, // HFP_LINK_SETTINGS_S3
1654     { 0x000c, 0x02, SCO_PACKET_TYPES_2EV3, true,  HFP_CODEC_CVSD }, // HFP_LINK_SETTINGS_S4
1655     { 0x0008, 0x02, SCO_PACKET_TYPES_EV3,  true,  HFP_CODEC_MSBC }, // HFP_LINK_SETTINGS_T1
1656     { 0x000d, 0x02, SCO_PACKET_TYPES_2EV3, true,  HFP_CODEC_MSBC }  // HFP_LINK_SETTINGS_T2
1657 };
1658 
1659 void hfp_setup_synchronous_connection(hfp_connection_t * hfp_connection){
1660     // all packet types, fixed bandwidth
1661     int setting = hfp_connection->link_setting;
1662     log_info("hfp_setup_synchronous_connection using setting nr %u", setting);
1663     sco_establishment_active = hfp_connection;
1664     uint16_t sco_voice_setting = hci_get_sco_voice_setting();
1665     if (hfp_connection->negotiated_codec == HFP_CODEC_MSBC){
1666 #ifdef ENABLE_BCM_PCM_WBS
1667         sco_voice_setting = 0x0063; // Transparent data, 16-bit for BCM controllers
1668 #else
1669         sco_voice_setting = 0x0043; // Transparent data, 8-bit otherwise
1670 #endif
1671     }
1672     // get packet types - bits 6-9 are 'don't allow'
1673     uint16_t packet_types = hfp_link_settings[setting].packet_types ^ 0x03c0;
1674     hci_send_cmd(&hci_setup_synchronous_connection, hfp_connection->acl_handle, 8000, 8000, hfp_link_settings[setting].max_latency,
1675         sco_voice_setting, hfp_link_settings[setting].retransmission_effort, packet_types);
1676 }
1677 
1678 #ifdef ENABLE_CC256X_ASSISTED_HFP
1679 void hfp_cc256x_prepare_for_sco(hfp_connection_t * hfp_connection){
1680     hfp_connection->cc256x_send_write_codec_config = true;
1681     if (hfp_connection->negotiated_codec == HFP_CODEC_MSBC){
1682         hfp_connection->cc256x_send_wbs_associate = true;
1683     }
1684 }
1685 
1686 void hfp_cc256x_write_codec_config(hfp_connection_t * hfp_connection){
1687     uint32_t sample_rate_hz;
1688     uint16_t clock_rate_khz;
1689     if (hfp_connection->negotiated_codec == HFP_CODEC_MSBC){
1690         clock_rate_khz = 512;
1691         sample_rate_hz = 16000;
1692     } else {
1693         clock_rate_khz = 256;
1694         sample_rate_hz = 8000;
1695     }
1696     uint8_t clock_direction = 0;        // master
1697     uint16_t frame_sync_duty_cycle = 0; // i2s with 50%
1698     uint8_t  frame_sync_edge = 1;       // rising edge
1699     uint8_t  frame_sync_polarity = 0;   // active high
1700     uint8_t  reserved = 0;
1701     uint16_t size = 16;
1702     uint16_t chan_1_offset = 1;
1703     uint16_t chan_2_offset = chan_1_offset + size;
1704     uint8_t  out_edge = 1;              // rising
1705     uint8_t  in_edge = 0;               // falling
1706     hci_send_cmd(&hci_ti_write_codec_config, clock_rate_khz, clock_direction, sample_rate_hz, frame_sync_duty_cycle,
1707                  frame_sync_edge, frame_sync_polarity, reserved,
1708                  size, chan_1_offset, out_edge, size, chan_1_offset, in_edge, reserved,
1709                  size, chan_2_offset, out_edge, size, chan_2_offset, in_edge, reserved);
1710 }
1711 #endif
1712 
1713 #ifdef ENABLE_BCM_PCM_WBS
1714 void hfp_bcm_prepare_for_sco(hfp_connection_t * hfp_connection){
1715     hfp_connection->bcm_send_write_i2spcm_interface_param = true;
1716     if (hfp_connection->negotiated_codec == HFP_CODEC_MSBC){
1717         hfp_connection->bcm_send_enable_wbs = true;
1718     }
1719 }
1720 void hfp_bcm_write_i2spcm_interface_param(hfp_connection_t * hfp_connection){
1721     uint8_t sample_rate = (hfp_connection->negotiated_codec == HFP_CODEC_MSBC) ? 1 : 0;
1722     // i2s enable, master, 8/16 kHz, 512 kHz
1723     hci_send_cmd(&hci_bcm_write_i2spcm_interface_paramhci_bcm_write_i2spcm_interface_param, 1, 1, sample_rate, 2);
1724 }
1725 #endif
1726 
1727 void hfp_set_hf_callback(btstack_packet_handler_t callback){
1728     hfp_hf_callback = callback;
1729 }
1730 
1731 void hfp_set_ag_callback(btstack_packet_handler_t callback){
1732     hfp_ag_callback = callback;
1733 }
1734 
1735 void hfp_set_ag_rfcomm_packet_handler(btstack_packet_handler_t handler){
1736     hfp_ag_rfcomm_packet_handler = handler;
1737 }
1738 
1739 void hfp_set_hf_rfcomm_packet_handler(btstack_packet_handler_t handler){
1740     hfp_hf_rfcomm_packet_handler = handler;
1741 }
1742 
1743 void hfp_init(void){
1744     hfp_allowed_sco_packet_types = SCO_PACKET_TYPES_ALL;
1745 }
1746 
1747 void hfp_deinit(void){
1748     hfp_connections = NULL;
1749     hfp_hf_callback = NULL;
1750     hfp_ag_callback = NULL;
1751     hfp_hf_rfcomm_packet_handler = NULL;
1752     hfp_ag_rfcomm_packet_handler = NULL;
1753     sco_establishment_active = NULL;
1754     (void) memset(&sdp_query_context, 0, sizeof(hfp_sdp_query_context_t));
1755     (void) memset(&hfp_handle_sdp_client_query_request, 0, sizeof(btstack_context_callback_registration_t));
1756 }
1757 
1758 void hfp_set_sco_packet_types(uint16_t packet_types){
1759     hfp_allowed_sco_packet_types = packet_types;
1760 }
1761 
1762 uint16_t hfp_get_sco_packet_types(void){
1763     return hfp_allowed_sco_packet_types;
1764 }
1765 
1766 hfp_link_settings_t hfp_next_link_setting(hfp_link_settings_t current_setting, bool local_eSCO_supported, bool remote_eSCO_supported, bool eSCO_S4_supported, uint8_t negotiated_codec){
1767     int8_t setting = (int8_t) current_setting;
1768     bool can_use_eSCO = local_eSCO_supported && remote_eSCO_supported;
1769     while (setting > 0){
1770         setting--;
1771         // skip if eSCO required but not available
1772         if (hfp_link_settings[setting].eSCO && !can_use_eSCO) continue;
1773         // skip if S4 but not supported
1774         if ((setting == (int8_t) HFP_LINK_SETTINGS_S4) && !eSCO_S4_supported) continue;
1775         // skip wrong codec
1776         if ( hfp_link_settings[setting].codec != negotiated_codec) continue;
1777         // skip disabled packet types
1778         uint16_t required_packet_types = hfp_link_settings[setting].packet_types;
1779         uint16_t allowed_packet_types  = hfp_allowed_sco_packet_types;
1780         if ((required_packet_types & allowed_packet_types) == 0) continue;
1781 
1782         // found matching setting
1783         return (hfp_link_settings_t) setting;
1784     }
1785     return HFP_LINK_SETTINGS_NONE;
1786 }
1787 
1788 static hfp_link_settings_t hfp_next_link_setting_for_connection(hfp_link_settings_t current_setting, hfp_connection_t * hfp_connection, uint8_t eSCO_S4_supported){
1789     bool local_eSCO_supported  = hci_extended_sco_link_supported();
1790     bool remote_eSCO_supported = hci_remote_esco_supported(hfp_connection->acl_handle);
1791     uint8_t negotiated_codec   = hfp_connection->negotiated_codec;
1792     return  hfp_next_link_setting(current_setting, local_eSCO_supported, remote_eSCO_supported, eSCO_S4_supported, negotiated_codec);
1793 }
1794 
1795 void hfp_init_link_settings(hfp_connection_t * hfp_connection, uint8_t eSCO_S4_supported){
1796     // get highest possible link setting
1797     hfp_connection->link_setting = hfp_next_link_setting_for_connection(HFP_LINK_SETTINGS_NONE, hfp_connection, eSCO_S4_supported);
1798     log_info("hfp_init_link_settings: %u", hfp_connection->link_setting);
1799 }
1800 
1801 #define HFP_HF_RX_DEBUG_PRINT_LINE 80
1802 
1803 void hfp_log_rfcomm_message(const char * tag, uint8_t * packet, uint16_t size){
1804 #ifdef ENABLE_LOG_INFO
1805     // encode \n\r
1806     char printable[HFP_HF_RX_DEBUG_PRINT_LINE+2];
1807     int i = 0;
1808     int pos;
1809     for (pos=0 ; (pos < size) && (i < (HFP_HF_RX_DEBUG_PRINT_LINE - 3)) ; pos++){
1810         switch (packet[pos]){
1811             case '\n':
1812                 printable[i++] = '\\';
1813                 printable[i++] = 'n';
1814                 break;
1815             case '\r':
1816                 printable[i++] = '\\';
1817                 printable[i++] = 'r';
1818                 break;
1819             default:
1820                 printable[i++] = packet[pos];
1821                 break;
1822         }
1823     }
1824     printable[i] = 0;
1825     log_info("%s: '%s'", tag, printable);
1826 #endif
1827 }
1828