hfp: fix indicators, add flags

This commit is contained in:
Milanka Ringwald 2015-08-13 20:55:21 +02:00
parent a93e7bb022
commit 783d2ff3ec
9 changed files with 182 additions and 90 deletions

View File

@ -63,15 +63,19 @@
#define HFP_HF_FEATURES_SIZE 10
#define HFP_AG_FEATURES_SIZE 12
static const char * hfp_hf_features[] = {
"EC and/or NR function",
"Three-way calling",
"CLI presentation capability",
"Voice recognition activation",
"Remote volume control",
"Enhanced call status",
"Enhanced call control",
"Codec negotiation",
"HF Indicators",
"eSCO S4 (and T2) Settings Supported",
"Reserved for future definition"
@ -494,7 +498,6 @@ uint32_t fromBinary(char *s) {
}
void hfp_parse(hfp_connection_t * context, uint8_t byte){
int i;
int value;
context->line_buffer[context->line_size] = 0;
@ -502,24 +505,48 @@ void hfp_parse(hfp_connection_t * context, uint8_t byte){
switch (context->parser_state){
case HFP_PARSER_CMD_HEADER: // header
if (byte == ':' || byte == '='){
if (context->wait_question_mark == 1 ) {
context->wait_question_mark = 0;
if (byte != '?'){
context->parser_state = HFP_PARSER_CMD_SEQUENCE;
context->line_buffer[context->line_size] = 0;
update_command(context);
context->parser_item_index = 0;
context->line_size = 0;
context->line_buffer[context->line_size++] = byte;
break;
}
}
if (byte == '?' || byte == '='){
context->line_buffer[context->line_size++] = byte;
if (byte == '='){
context->wait_question_mark = 1;
}
}
if (byte == ':' || byte == '?'){
context->parser_state = HFP_PARSER_CMD_SEQUENCE;
context->line_buffer[context->line_size] = 0;
update_command(context);
context->line_size = 0;
context->parser_item_index = 0;
update_command(context);
context->wait_question_mark = 0;
return;
}
if (byte == '\n' || byte == '\r'){
context->line_buffer[context->line_size] = 0;
if (context->line_size == 2){
printf("Parsed OK\n");
update_command(context);
}
context->line_size = 0;
context->parser_item_index = 0;
return;
}
context->line_buffer[context->line_size++] = byte;
break;
@ -539,12 +566,7 @@ void hfp_parse(hfp_connection_t * context, uint8_t byte){
switch (context->command){
case HFP_CMD_SUPPORTED_FEATURES:
context->remote_supported_features = 0;
for (i=0; i<16; i++){
if (context->line_buffer[i] == '1'){
context->remote_supported_features = store_bit(context->remote_supported_features,15-i,1);
}
}
context->remote_supported_features = atoi((char*)context->line_buffer);
printf("Parsed supported feature %d\n", context->remote_supported_features);
context->parser_state = HFP_PARSER_CMD_HEADER;
break;
@ -581,17 +603,27 @@ void hfp_parse(hfp_connection_t * context, uint8_t byte){
}
break;
case HFP_CMD_GENERIC_STATUS_INDICATOR:
printf("Parsed Generic status indicator: %s\n", context->line_buffer);
context->generic_status_indicators[context->parser_item_index].uuid = (uint16_t)atoi((char*)context->line_buffer);
context->parser_item_index++;
context->generic_status_indicators_nr = context->parser_item_index;
break;
case HFP_CMD_GENERIC_STATUS_INDICATOR_STATE:
// HF parses inital AG gen. ind. state
printf("Parsed List generic status indicator %s state: ", context->line_buffer);
context->parser_state = HFP_PARSER_CMD_INDICATOR_STATUS;
context->parser_item_index = (uint8_t)atoi((char*)context->line_buffer);
printf("parser HFP_CMD_GENERIC_STATUS_INDICATOR 1 (%d, %d, %d)\n",
context->list_generic_status_indicators,
context->retrieve_generic_status_indicators,
context->retrieve_generic_status_indicators_state);
if (context->retrieve_generic_status_indicators == 1 || context->list_generic_status_indicators == 1){
printf("Parsed Generic status indicator: %s\n", context->line_buffer);
context->generic_status_indicators[context->parser_item_index].uuid = (uint16_t)atoi((char*)context->line_buffer);
context->parser_item_index++;
context->generic_status_indicators_nr = context->parser_item_index;
break;
}
printf("parser HFP_CMD_GENERIC_STATUS_INDICATOR 2\n");
if (context->retrieve_generic_status_indicators_state == 1){
// HF parses inital AG gen. ind. state
printf("Parsed List generic status indicator %s state: ", context->line_buffer);
context->parser_state = HFP_PARSER_CMD_INDICATOR_STATUS;
context->parser_item_index = (uint8_t)atoi((char*)context->line_buffer);
break;
}
break;
case HFP_CMD_ENABLE_INDIVIDUAL_AG_INDICATOR_STATUS_UPDATE:
// AG parses new gen. ind. state
printf("Parsed Enable ag indicator state: %s\n", context->line_buffer);
@ -602,10 +634,10 @@ void hfp_parse(hfp_connection_t * context, uint8_t byte){
context->parser_item_index++;
break;
case HFP_CMD_TRANSFER_AG_INDICATOR_STATUS:
printf("Parsed AG indicator status: %s\n", context->line_buffer);
// indicators are indexed starting with 1
context->parser_item_index = atoi((char *)&context->line_buffer[0]) - 1;
context->parser_state = HFP_PARSER_CMD_INDICATOR_STATUS;
printf("Parsed status of the AG indicator %d, status ", context->parser_item_index);
break;
case HFP_CMD_QUERY_OPERATOR_SELECTION:
printf("Parsed Network operator: %s\n", context->line_buffer);
@ -638,7 +670,6 @@ void hfp_parse(hfp_connection_t * context, uint8_t byte){
context->line_size = 0;
if (byte == '\n' || byte == '\r'){
printf("parse done 1, state %d\n", context->parser_state);
context->parser_state = HFP_PARSER_CMD_HEADER;
context->parser_item_index = 0;
break;
@ -688,7 +719,7 @@ void hfp_parse(hfp_connection_t * context, uint8_t byte){
printf("%s\n", context->line_buffer);
// HF stores inital AG gen. ind. state
switch (context->command){
case HFP_CMD_GENERIC_STATUS_INDICATOR_STATE:
case HFP_CMD_GENERIC_STATUS_INDICATOR:
context->generic_status_indicators[context->parser_item_index].state = (uint8_t)atoi((char*)context->line_buffer);
break;
case HFP_CMD_TRANSFER_AG_INDICATOR_STATUS:
@ -742,7 +773,6 @@ void hfp_parse(hfp_connection_t * context, uint8_t byte){
context->line_size = 0;
context->parser_item_index++;
context->ag_indicators_nr = context->parser_item_index;
printf("parser ag nr %d \n", context->ag_indicators_nr);
break;
}

View File

@ -125,13 +125,13 @@ typedef enum {
HFP_CMD_OK,
HFP_CMD_SUPPORTED_FEATURES,
HFP_CMD_AVAILABLE_CODECS,
HFP_CMD_INDICATOR,
HFP_CMD_INDICATOR, // 5
HFP_CMD_ENABLE_INDICATOR_STATUS_UPDATE,
HFP_CMD_ENABLE_INDIVIDUAL_AG_INDICATOR_STATUS_UPDATE,
HFP_CMD_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES,
HFP_CMD_LIST_GENERIC_STATUS_INDICATOR,
HFP_CMD_GENERIC_STATUS_INDICATOR,
HFP_CMD_GENERIC_STATUS_INDICATOR_STATE,
HFP_CMD_GENERIC_STATUS_INDICATOR,
HFP_CMD_TRANSFER_AG_INDICATOR_STATUS,
HFP_CMD_QUERY_OPERATOR_SELECTION
} hfp_command_t;
@ -255,18 +255,17 @@ typedef struct hfp_connection {
// Retrieved during service level connection establishment, not used yet
uint8_t negotiated_codec;
// TODO: remove
hfp_command_t sent_command;
// TODO: put these bit flags in a bitmap
uint8_t wait_ok;
uint8_t wait_question_mark;
uint8_t retrieve_ag_indicators; // HFP_CMD_INDICATOR, check if needed
uint8_t retrieve_ag_indicators_status;
uint8_t list_generic_status_indicators;
uint8_t retrieve_generic_status_indicators;
uint8_t retrieve_generic_status_indicators_state;
uint8_t list_generic_status_indicators; // HFP_CMD_LIST_GENERIC_STATUS_INDICATOR
uint8_t retrieve_generic_status_indicators; // HFP_CMD_GENERIC_STATUS_INDICATOR
uint8_t retrieve_generic_status_indicators_state; // HFP_CMD_GENERIC_STATUS_INDICATOR_STATE
uint8_t operator_name_format;
uint8_t operator_name;

View File

@ -79,11 +79,20 @@ hfp_generic_status_indicator_t * get_hfp_generic_status_indicators();
int get_hfp_generic_status_indicators_nr();
void set_hfp_generic_status_indicators(hfp_generic_status_indicator_t * indicators, int indicator_nr);
hfp_ag_indicator_t * get_hfp_ag_indicators(){
return (hfp_ag_indicator_t *)&hfp_ag_indicators;
hfp_ag_indicator_t * get_hfp_ag_indicators(hfp_connection_t * context){
if (context->ag_indicators_nr != hfp_ag_indicators_nr){
context->ag_indicators_nr = hfp_ag_indicators_nr;
memcpy(context->ag_indicators, hfp_ag_indicators, hfp_ag_indicators_nr * sizeof(hfp_ag_indicator_t));
}
return (hfp_ag_indicator_t *)&(context->ag_indicators);
}
int get_hfp_ag_indicators_nr(){
return hfp_ag_indicators_nr;
int get_hfp_ag_indicators_nr(hfp_connection_t * context){
if (context->ag_indicators_nr != hfp_ag_indicators_nr){
context->ag_indicators_nr = hfp_ag_indicators_nr;
memcpy(context->ag_indicators, hfp_ag_indicators, hfp_ag_indicators_nr * sizeof(hfp_ag_indicator_t));
}
return context->ag_indicators_nr;
}
void set_hfp_ag_indicators(hfp_ag_indicator_t * indicators, int indicator_nr){
memcpy(hfp_ag_indicators, indicators, indicator_nr * sizeof(hfp_ag_indicator_t));
@ -156,15 +165,21 @@ int hfp_ag_retrieve_codec_cmd(uint16_t cid){
return hfp_ag_ok(cid);
}
int hfp_ag_indicators_join(char * buffer, int buffer_size){
if (buffer_size < hfp_ag_indicators_nr * (1 + sizeof(hfp_ag_indicator_t))) return 0;
int hfp_ag_indicators_join(char * buffer, int buffer_size, hfp_connection_t * context){
if (buffer_size < get_hfp_ag_indicators_nr(context) * (1 + sizeof(hfp_ag_indicator_t))) return 0;
int i;
int offset = 0;
for (i = 0; i < hfp_ag_indicators_nr-1; i++) {
offset += snprintf(buffer+offset, buffer_size-offset, "(\"%s\",(%d,%d)),", hfp_ag_indicators[i].name, hfp_ag_indicators[i].min_range, hfp_ag_indicators[i].max_range);;
for (i = 0; i < get_hfp_ag_indicators_nr(context)-1; i++) {
offset += snprintf(buffer+offset, buffer_size-offset, "(\"%s\",(%d,%d)),",
get_hfp_ag_indicators(context)[i].name,
get_hfp_ag_indicators(context)[i].min_range,
get_hfp_ag_indicators(context)[i].max_range);
}
if (i<hfp_ag_indicators_nr){
offset += snprintf(buffer+offset, buffer_size-offset, "(\"%s\",(%d,%d))", hfp_ag_indicators[i].name, hfp_ag_indicators[i].min_range, hfp_ag_indicators[i].max_range);
if ( i < get_hfp_ag_indicators_nr(context)){
offset += snprintf(buffer+offset, buffer_size-offset, "(\"%s\",(%d,%d))",
get_hfp_ag_indicators(context)[i].name,
get_hfp_ag_indicators(context)[i].min_range,
get_hfp_ag_indicators(context)[i].max_range);
}
return offset;
}
@ -218,10 +233,14 @@ int hfp_ag_call_services_join(char * buffer, int buffer_size){
return offset;
}
int hfp_ag_retrieve_indicators_cmd(uint16_t cid){
char buffer[150];
int hfp_ag_retrieve_indicators_cmd(uint16_t cid, hfp_connection_t * context){
char buffer[250];
int offset = snprintf(buffer, sizeof(buffer), "\r\n%s:", HFP_INDICATOR);
offset += hfp_ag_indicators_join(buffer+offset, sizeof(buffer)-offset);
offset += hfp_ag_indicators_join(buffer+offset, sizeof(buffer)-offset, context);
buffer[offset] = 0;
printf("hfp_ag_retrieve_indicators_cmd send %s\n", buffer+2);
offset += snprintf(buffer+offset, sizeof(buffer)-offset, "\r\n\r\nOK\r\n");
buffer[offset] = 0;
return send_str_over_rfcomm(cid, buffer);
@ -231,6 +250,10 @@ int hfp_ag_retrieve_indicators_status_cmd(uint16_t cid){
char buffer[40];
int offset = snprintf(buffer, sizeof(buffer), "\r\n%s:", HFP_INDICATOR);
offset += hfp_ag_indicators_status_join(buffer+offset, sizeof(buffer)-offset);
buffer[offset] = 0;
printf("send %s\n", buffer+2);
offset += snprintf(buffer+offset, sizeof(buffer)-offset, "\r\n\r\nOK\r\n");
buffer[offset] = 0;
return send_str_over_rfcomm(cid, buffer);
@ -246,6 +269,10 @@ int hfp_ag_retrieve_can_hold_call_cmd(uint16_t cid){
char buffer[100];
int offset = snprintf(buffer, sizeof(buffer), "\r\n%s:", HFP_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES);
offset += hfp_ag_call_services_join(buffer+offset, sizeof(buffer)-offset);
buffer[offset] = 0;
printf("send %s\n", buffer+2);
offset += snprintf(buffer+offset, sizeof(buffer)-offset, "\r\n\r\nOK\r\n");
buffer[offset] = 0;
return send_str_over_rfcomm(cid, buffer);
@ -260,6 +287,10 @@ int hfp_ag_retrieve_supported_generic_status_indicators_cmd(uint16_t cid){
char buffer[40];
int offset = snprintf(buffer, sizeof(buffer), "\r\n%s:", HFP_GENERIC_STATUS_INDICATOR);
offset += hfp_hf_indicators_join(buffer+offset, sizeof(buffer)-offset);
buffer[offset] = 0;
printf("send %s\n", buffer+2);
offset += snprintf(buffer+offset, sizeof(buffer)-offset, "\r\n\r\nOK\r\n");
buffer[offset] = 0;
return send_str_over_rfcomm(cid, buffer);
@ -268,6 +299,10 @@ int hfp_ag_retrieve_supported_generic_status_indicators_cmd(uint16_t cid){
int hfp_ag_retrieve_initital_supported_generic_status_indicators_cmd(uint16_t cid){
char buffer[40];
int offset = hfp_hf_indicators_initial_status_join(buffer, sizeof(buffer));
buffer[offset] = 0;
printf("send %s\n", buffer+2);
offset += snprintf(buffer+offset, sizeof(buffer)-offset, "\r\nOK\r\n");
buffer[offset] = 0;
return send_str_over_rfcomm(cid, buffer);
@ -291,10 +326,9 @@ int hfp_ag_report_network_operator_name_cmd(uint16_t cid, hfp_network_opearator_
void update_command(hfp_connection_t * context){
context->command = HFP_CMD_NONE;
printf("Received %s\n", context->line_buffer);
if (strncmp((char *)context->line_buffer+2, HFP_SUPPORTED_FEATURES, strlen(HFP_SUPPORTED_FEATURES)) == 0){
context->command = HFP_CMD_SUPPORTED_FEATURES;
context->command = HFP_CMD_SUPPORTED_FEATURES;
return;
}
@ -329,6 +363,19 @@ void update_command(hfp_connection_t * context){
if (strncmp((char *)context->line_buffer+2, HFP_GENERIC_STATUS_INDICATOR, strlen(HFP_GENERIC_STATUS_INDICATOR)) == 0){
context->command = HFP_CMD_GENERIC_STATUS_INDICATOR;
if (strncmp((char *)context->line_buffer+strlen(HFP_GENERIC_STATUS_INDICATOR)+2, "=?", 2) == 0){
context->list_generic_status_indicators = 0;
context->retrieve_generic_status_indicators = 1;
context->retrieve_generic_status_indicators_state = 0;
} else if (strncmp((char *)context->line_buffer+strlen(HFP_GENERIC_STATUS_INDICATOR)+2, "=", 1) == 0){
context->list_generic_status_indicators = 1;
context->retrieve_generic_status_indicators = 0;
context->retrieve_generic_status_indicators_state = 0;
} else {
context->list_generic_status_indicators = 0;
context->retrieve_generic_status_indicators = 0;
context->retrieve_generic_status_indicators_state = 1;
}
return;
}
@ -352,8 +399,10 @@ void update_command(hfp_connection_t * context){
void hfp_run_for_context(hfp_connection_t *context){
// printf(" hfp_run_for_context \n");
if (!context) return;
if (!rfcomm_can_send_packet_now(context->rfcomm_cid)) return;
//printf(" hfp_run_for_context 1 state %d, command %d\n", context->state, context->command);
if (context->state == HFP_SERVICE_LEVEL_CONNECTION_ESTABLISHED){
if (context->enable_status_update_for_ag_indicators == 1){
@ -367,7 +416,6 @@ void hfp_run_for_context(hfp_connection_t *context){
return;
}
}
return;
}
switch(context->command){
@ -399,7 +447,7 @@ void hfp_run_for_context(hfp_connection_t *context){
switch(context->state){
case HFP_W4_RETRIEVE_INDICATORS:
if (context->retrieve_ag_indicators == 0) break;
hfp_ag_retrieve_indicators_cmd(context->rfcomm_cid);
hfp_ag_retrieve_indicators_cmd(context->rfcomm_cid, context);
context->state = HFP_W4_RETRIEVE_INDICATORS_STATUS;
break;
case HFP_W4_RETRIEVE_INDICATORS_STATUS:
@ -451,17 +499,22 @@ void hfp_run_for_context(hfp_connection_t *context){
case HFP_CMD_GENERIC_STATUS_INDICATOR:
switch(context->state){
case HFP_W4_LIST_GENERIC_STATUS_INDICATORS:
if (context->list_generic_status_indicators == 0) break;
hfp_ag_list_supported_generic_status_indicators_cmd(context->rfcomm_cid);
context->state = HFP_W4_RETRIEVE_GENERIC_STATUS_INDICATORS;
context->list_generic_status_indicators = 0;
break;
case HFP_W4_RETRIEVE_GENERIC_STATUS_INDICATORS:
if (context->retrieve_generic_status_indicators == 0) break;
hfp_ag_retrieve_supported_generic_status_indicators_cmd(context->rfcomm_cid);
context->state = HFP_W4_RETRIEVE_INITITAL_STATE_GENERIC_STATUS_INDICATORS;
context->retrieve_generic_status_indicators = 0;
break;
case HFP_W4_RETRIEVE_INITITAL_STATE_GENERIC_STATUS_INDICATORS:
if (context->retrieve_generic_status_indicators_state == 0) break;
hfp_ag_retrieve_initital_supported_generic_status_indicators_cmd(context->rfcomm_cid);
context->state = HFP_SERVICE_LEVEL_CONNECTION_ESTABLISHED;
context->retrieve_generic_status_indicators_state = 0;
hfp_emit_event(hfp_callback, HFP_SUBEVENT_SERVICE_LEVEL_CONNECTION_ESTABLISHED, 0);
break;
default:
@ -475,11 +528,13 @@ void hfp_run_for_context(hfp_connection_t *context){
hfp_ag_error(context->rfcomm_cid);
break;
}
hfp_ag_ok(context->rfcomm_cid);
hfp_ag_ok(context->rfcomm_cid);
context->operator_name_format = 0;
break;
}
if (context->operator_name == 1){
hfp_ag_report_network_operator_name_cmd(context->rfcomm_cid, context->network_operator);
context->operator_name = 0;
break;
}
break;
@ -508,15 +563,15 @@ static void hfp_handle_rfcomm_event(uint8_t packet_type, uint16_t channel, uint8
context->state = HFP_W4_EXCHANGE_SUPPORTED_FEATURES;
}
printf("hfp_handle_rfcomm_event %s\n", &packet[0]);
packet[size] = 0;
printf("\nparse command: %s\n", packet);
int pos;
for (pos = 0; pos < size ; pos++){
hfp_parse(context, packet[pos]);
// trigger next action after CMD received
if (context->command == HFP_CMD_NONE) continue;
// hfp_run_for_context(context);
//hfp_run_for_context(context);
}
}
@ -565,6 +620,9 @@ void hfp_ag_init(uint16_t rfcomm_channel_nr, uint32_t supported_features,
hfp_ag_indicators_nr = ag_indicators_nr;
memcpy(hfp_ag_indicators, ag_indicators, ag_indicators_nr * sizeof(hfp_ag_indicator_t));
for (i=0; i<hfp_ag_indicators_nr; i++){
printf("ag ind %s\n", hfp_ag_indicators[i].name);
}
set_hfp_generic_status_indicators(hf_indicators, hf_indicators_nr);

View File

@ -249,19 +249,22 @@ static void hfp_run_for_context(hfp_connection_t * context){
case HFP_LIST_GENERIC_STATUS_INDICATORS:
hfp_hs_list_supported_generic_status_indicators_cmd(context->rfcomm_cid);
context->state = HFP_W4_LIST_GENERIC_STATUS_INDICATORS;
context->sent_command = HFP_CMD_LIST_GENERIC_STATUS_INDICATOR;
context->list_generic_status_indicators = 1;
context->retrieve_generic_status_indicators = 0;
context->retrieve_generic_status_indicators_state = 0;
break;
case HFP_RETRIEVE_GENERIC_STATUS_INDICATORS:
hfp_hs_retrieve_supported_generic_status_indicators_cmd(context->rfcomm_cid);
context->state = HFP_W4_RETRIEVE_GENERIC_STATUS_INDICATORS;
context->sent_command = HFP_CMD_GENERIC_STATUS_INDICATOR;
context->list_generic_status_indicators = 0;
context->retrieve_generic_status_indicators = 1;
context->retrieve_generic_status_indicators_state = 0;
break;
case HFP_RETRIEVE_INITITAL_STATE_GENERIC_STATUS_INDICATORS:
hfp_hs_list_initital_supported_generic_status_indicators_cmd(context->rfcomm_cid);
context->state = HFP_W4_RETRIEVE_INITITAL_STATE_GENERIC_STATUS_INDICATORS;
context->sent_command = HFP_CMD_GENERIC_STATUS_INDICATOR_STATE;
context->list_generic_status_indicators = 0;
context->retrieve_generic_status_indicators = 0;
context->retrieve_generic_status_indicators_state = 1;
break;
@ -319,54 +322,44 @@ void update_command(hfp_connection_t * context){
context->command = HFP_CMD_NONE;
if (strncmp((char *)context->line_buffer, HFP_ERROR, strlen(HFP_ERROR)) == 0){
context->command = HFP_CMD_ERROR;
printf("Received ERROR\n");
}
if (strncmp((char *)context->line_buffer, HFP_OK, strlen(HFP_OK)) == 0){
context->command = HFP_CMD_OK;
printf("Received OK\n");
return;
}
if (strncmp((char *)context->line_buffer, HFP_SUPPORTED_FEATURES, strlen(HFP_SUPPORTED_FEATURES)) == 0){
printf("Received +BRSF\n");
context->command = HFP_CMD_SUPPORTED_FEATURES;
return;
}
if (strncmp((char *)context->line_buffer, HFP_INDICATOR, strlen(HFP_INDICATOR)) == 0){
printf("Received +CIND, %d\n", context->sent_command);
context->command = HFP_CMD_INDICATOR;
return;
}
if (strncmp((char *)context->line_buffer, HFP_AVAILABLE_CODECS, strlen(HFP_AVAILABLE_CODECS)) == 0){
printf("Received +BAC\n");
context->command = HFP_CMD_AVAILABLE_CODECS;
return;
}
if (strncmp((char *)context->line_buffer, HFP_ENABLE_STATUS_UPDATE_FOR_AG_INDICATORS, strlen(HFP_ENABLE_STATUS_UPDATE_FOR_AG_INDICATORS)) == 0){
printf("Received +CMER\n");
context->command = HFP_CMD_ENABLE_INDICATOR_STATUS_UPDATE;
return;
}
if (strncmp((char *)context->line_buffer, HFP_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES, strlen(HFP_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES)) == 0){
printf("Received +CHLD\n");
context->command = HFP_CMD_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES;
return;
}
if (strncmp((char *)context->line_buffer, HFP_GENERIC_STATUS_INDICATOR, strlen(HFP_GENERIC_STATUS_INDICATOR)) == 0){
printf("Received +BIND\n");
context->command = context->sent_command;
printf("Received +BIND %d\n", context->sent_command);
context->command = HFP_CMD_GENERIC_STATUS_INDICATOR;
return;
}
if (strncmp((char *)context->line_buffer, HFP_TRANSFER_AG_INDICATOR_STATUS, strlen(HFP_UPDATE_ENABLE_STATUS_FOR_INDIVIDUAL_AG_INDICATORS)) == 0){
printf("Received +CIEV\n");
context->command = HFP_CMD_TRANSFER_AG_INDICATOR_STATUS;
return;
}
@ -423,15 +416,17 @@ void handle_switch_on_ok(hfp_connection_t *context){
case HFP_W4_LIST_GENERIC_STATUS_INDICATORS:
context->state = HFP_RETRIEVE_GENERIC_STATUS_INDICATORS;
context->retrieve_generic_status_indicators = 0;
break;
case HFP_W4_RETRIEVE_GENERIC_STATUS_INDICATORS:
context->state = HFP_RETRIEVE_INITITAL_STATE_GENERIC_STATUS_INDICATORS;
context->retrieve_generic_status_indicators = 0;
break;
case HFP_W4_RETRIEVE_INITITAL_STATE_GENERIC_STATUS_INDICATORS:
printf("Supported initial state generic status indicators \n");
context->state = HFP_SERVICE_LEVEL_CONNECTION_ESTABLISHED;
context->retrieve_generic_status_indicators_state = 0;
hfp_emit_event(hfp_callback, HFP_SUBEVENT_SERVICE_LEVEL_CONNECTION_ESTABLISHED, 0);
break;
@ -454,7 +449,7 @@ static void hfp_handle_rfcomm_event(uint8_t packet_type, uint16_t channel, uint8
packet[size] = 0;
int pos;
printf("parse command: %s, state: %d\n", packet, context->parser_state);
printf("parse command: %s\n", packet+2);
for (pos = 0; pos < size ; pos++){
hfp_parse(context, packet[pos]);

View File

@ -90,15 +90,15 @@ TEST_GROUP(HFPParser){
};
TEST(HFPParser, HFP_AG_SUPPORTED_FEATURES){
sprintf(packet, "\r\nAT%s=0000001111101111\r\n", HFP_SUPPORTED_FEATURES);
sprintf(packet, "\r\nAT%s=159\r\n", HFP_SUPPORTED_FEATURES);
context.wait_question_mark = 0;
for (pos = 0; pos < strlen(packet); pos++){
hfp_parse(&context, packet[pos]);
}
CHECK_EQUAL(HFP_CMD_SUPPORTED_FEATURES, context.command);
CHECK_EQUAL(1007, context.remote_supported_features);
CHECK_EQUAL(159, context.remote_supported_features);
}
TEST(HFPParser, HFP_AG_AVAILABLE_CODECS){
sprintf(packet, "\r\nAT%s=0,1,2\r\n", HFP_AVAILABLE_CODECS);
for (pos = 0; pos < strlen(packet); pos++){
@ -111,22 +111,27 @@ TEST(HFPParser, HFP_AG_AVAILABLE_CODECS){
}
}
TEST(HFPParser, HFP_AG_GENERIC_STATUS_INDICATOR){
sprintf(packet, "\r\nAT%s=0,1\r\n", HFP_GENERIC_STATUS_INDICATOR);
context.sent_command = HFP_CMD_GENERIC_STATUS_INDICATOR;
sprintf(packet, "\r\nAT%s=0,1,2,3,4\r\n", HFP_GENERIC_STATUS_INDICATOR);
for (pos = 0; pos < strlen(packet); pos++){
hfp_parse(&context, packet[pos]);
}
CHECK_EQUAL(context.command, HFP_CMD_GENERIC_STATUS_INDICATOR);
CHECK_EQUAL(context.list_generic_status_indicators, 1);
CHECK_EQUAL(context.retrieve_generic_status_indicators, 0);
CHECK_EQUAL(context.retrieve_generic_status_indicators_state, 0);
CHECK_EQUAL(HFP_CMD_GENERIC_STATUS_INDICATOR, context.command);
CHECK_EQUAL(2, context.generic_status_indicators_nr);
CHECK_EQUAL(5, context.generic_status_indicators_nr);
for (pos = 0; pos < context.generic_status_indicators_nr; pos++){
CHECK_EQUAL(pos, context.generic_status_indicators[pos].uuid);
}
}
TEST(HFPParser, HFP_AG_ENABLE_INDICATOR_STATUS_UPDATE){
sprintf(packet, "\r\nAT%s=3,0,0,1\r\n", HFP_ENABLE_STATUS_UPDATE_FOR_AG_INDICATORS);
for (pos = 0; pos < strlen(packet); pos++){

View File

@ -85,7 +85,7 @@ TEST(HFPParser, HFP_HF_OK){
}
TEST(HFPParser, HFP_HF_SUPPORTED_FEATURES){
sprintf(packet, "\r\n%s:0000001111101111\r\n", HFP_SUPPORTED_FEATURES);
sprintf(packet, "\r\n%s:1007\r\n", HFP_SUPPORTED_FEATURES);
for (pos = 0; pos < strlen(packet); pos++){
hfp_parse(&context, packet[pos]);
}
@ -157,15 +157,19 @@ TEST(HFPParser, HFP_HF_SUPPORT_CALL_HOLD_AND_MULTIPARTY_SERVICES){
}
TEST(HFPParser, HFP_HF_GENERIC_STATUS_INDICATOR){
sprintf(packet, "\r\n%s:0,1\r\n", HFP_GENERIC_STATUS_INDICATOR);
context.sent_command = HFP_CMD_GENERIC_STATUS_INDICATOR;
sprintf(packet, "\r\n%s:0,1,2,3,4\r\n", HFP_GENERIC_STATUS_INDICATOR);
context.command = HFP_CMD_GENERIC_STATUS_INDICATOR;
context.list_generic_status_indicators = 0;
context.retrieve_generic_status_indicators = 1;
context.retrieve_generic_status_indicators_state = 0;
for (pos = 0; pos < strlen(packet); pos++){
hfp_parse(&context, packet[pos]);
}
CHECK_EQUAL(HFP_CMD_GENERIC_STATUS_INDICATOR, context.command);
CHECK_EQUAL(2, context.generic_status_indicators_nr);
CHECK_EQUAL(5, context.generic_status_indicators_nr);
for (pos = 0; pos < context.generic_status_indicators_nr; pos++){
CHECK_EQUAL(pos, context.generic_status_indicators[pos].uuid);
@ -174,13 +178,16 @@ TEST(HFPParser, HFP_HF_GENERIC_STATUS_INDICATOR){
TEST(HFPParser, HFP_HF_GENERIC_STATUS_INDICATOR_STATE){
sprintf(packet, "\r\n%s:0,1\r\n", HFP_GENERIC_STATUS_INDICATOR);
context.sent_command = HFP_CMD_GENERIC_STATUS_INDICATOR_STATE;
context.command = HFP_CMD_GENERIC_STATUS_INDICATOR;
context.list_generic_status_indicators = 0;
context.retrieve_generic_status_indicators = 0;
context.retrieve_generic_status_indicators_state = 1;
for (pos = 0; pos < strlen(packet); pos++){
hfp_parse(&context, packet[pos]);
}
CHECK_EQUAL(HFP_CMD_GENERIC_STATUS_INDICATOR_STATE, context.command);
CHECK_EQUAL(HFP_CMD_GENERIC_STATUS_INDICATOR, context.command);
CHECK_EQUAL(1, context.generic_status_indicators[0].state);
}

View File

@ -18,11 +18,11 @@ VPATH += ${BTSTACK_ROOT}/platforms/posix/src
VPATH += ${BTSTACK_ROOT}/platforms/libusb
# use pkg-config
# CFLAGS += $(shell pkg-config libusb-1.0 --cflags)
# LDFLAGS += $(shell pkg-config libusb-1.0 --libs)
CFLAGS += $(shell pkg-config libusb-1.0 --cflags)
LDFLAGS += $(shell pkg-config libusb-1.0 --libs)
# hard coded flags for libusb in /usr/local/lib
CFLAGS += -I/usr/local/include
LDFLAGS += -L/usr/local/lib -lusb-1.0
# CFLAGS += -I/usr/local/include
# LDFLAGS += -L/usr/local/lib -lusb-1.0
EXAMPLES = hfp_hf_test hfp_ag_test ble_peripheral_test ble_central_test l2cap_test classic_test bnep_test hsp_ag_test hsp_hs_test

View File

@ -72,7 +72,6 @@ const uint8_t rfcomm_channel_nr = 1;
const char hfp_ag_service_name[] = "BTstack HFP AG Test";
static bd_addr_t pts_addr = {0x00,0x1b,0xDC,0x07,0x32,0xEF};
static bd_addr_t local_mac = {0x04, 0x0C, 0xCE, 0xE4, 0x85, 0xD3};
static bd_addr_t speaker = {0x00, 0x21, 0x3C, 0xAC, 0xF7, 0x38};
static uint8_t codecs[1] = {HFP_CODEC_CVSD};

View File

@ -73,7 +73,6 @@ const uint8_t rfcomm_channel_nr = 1;
const char hfp_hf_service_name[] = "BTstack HFP HF Test";
static bd_addr_t pts_addr = {0x00,0x1b,0xDC,0x07,0x32,0xEF};
static bd_addr_t local_mac = {0x04, 0x0C, 0xCE, 0xE4, 0x85, 0xD3};
static bd_addr_t phone_addr = {0xD8,0xBb,0x2C,0xDf,0xF1,0x08};
static bd_addr_t device_addr;