diff --git a/src/hci.c b/src/hci.c index a7afea634..e9dc84e36 100644 --- a/src/hci.c +++ b/src/hci.c @@ -564,7 +564,19 @@ static void event_handler(uint8_t *packet, int size){ case HCI_EVENT_IO_CAPABILITY_REQUEST: hci_add_connection_flags_for_flipped_bd_addr(&packet[2], RECV_IO_CAPABILITIES_REQUEST); if (hci_stack.ssp_io_capability == SSP_IO_CAPABILITY_UNKNOWN) break; - hci_add_connection_flags_for_flipped_bd_addr(&packet[2], SENT_IO_CAPABILITIES_REPLY); + hci_add_connection_flags_for_flipped_bd_addr(&packet[2], SEND_IO_CAPABILITIES_REPLY); + break; + + case HCI_EVENT_USER_CONFIRMATION_REQUEST: + hci_add_connection_flags_for_flipped_bd_addr(&packet[2], RECV_USER_CONFIRM_REQUEST); + if (!hci_stack.ssp_auto_accept) break; + hci_add_connection_flags_for_flipped_bd_addr(&packet[2], SEND_USER_CONFIRM_REPLY); + break; + + case HCI_EVENT_USER_PASSKEY_REQUEST: + hci_add_connection_flags_for_flipped_bd_addr(&packet[2], RECV_USER_PASSKEY_REQUEST); + if (!hci_stack.ssp_auto_accept) break; + hci_add_connection_flags_for_flipped_bd_addr(&packet[2], SEND_USER_PASSKEY_REPLY); break; #ifndef EMBEDDED @@ -1056,30 +1068,27 @@ void hci_run(){ uint8_t reason = hci_stack.decline_reason; hci_stack.decline_reason = 0; hci_send_cmd(&hci_reject_connection_request, hci_stack.decline_addr, reason); + return; } - if (!hci_can_send_packet_now(HCI_COMMAND_DATA_PACKET)) return; - // send scan enable if (hci_stack.state == HCI_STATE_WORKING && hci_stack.new_scan_enable_value != 0xff){ hci_send_cmd(&hci_write_scan_enable, hci_stack.new_scan_enable_value); hci_stack.new_scan_enable_value = 0xff; + return; } // send pending HCI commands for (it = (linked_item_t *) hci_stack.connections; it ; it = it->next){ - if (!hci_can_send_packet_now(HCI_COMMAND_DATA_PACKET)) return; - connection = (hci_connection_t *) it; if (connection->state == RECEIVED_CONNECTION_REQUEST){ log_info("sending hci_accept_connection_request\n"); hci_send_cmd(&hci_accept_connection_request, connection->address, 1); connection->state = ACCEPTED_CONNECTION_REQUEST; + return; } - - if (!hci_can_send_packet_now(HCI_COMMAND_DATA_PACKET)) return; if (connection->authentication_flags & HANDLE_LINK_KEY_REQUEST){ link_key_t link_key; @@ -1090,18 +1099,28 @@ void hci_run(){ hci_send_cmd(&hci_link_key_request_negative_reply, connection->address); } connectionClearAuthenticationFlags(connection, HANDLE_LINK_KEY_REQUEST); + return; } - if (!hci_can_send_packet_now(HCI_COMMAND_DATA_PACKET)) return; + if (connection->authentication_flags & SEND_IO_CAPABILITIES_REPLY){ + hci_send_cmd(&hci_io_capability_request_reply, &connection->address, hci_stack.ssp_io_capability, NULL, hci_stack.ssp_authentication_requirement); + connectionClearAuthenticationFlags(connection, SEND_IO_CAPABILITIES_REPLY); + return; + } - if (connection->authentication_flags & SENT_IO_CAPABILITIES_REPLY){ - hci_send_cmd(&hci_io_capability_request_reply, hci_stack.ssp_io_capability, NULL, hci_stack.ssp_authentication_requirement); - connectionClearAuthenticationFlags(connection, SENT_IO_CAPABILITIES_REPLY); + if (connection->authentication_flags & SEND_USER_CONFIRM_REPLY){ + hci_send_cmd(&hci_user_confirmation_request_reply, &connection->address); + connectionClearAuthenticationFlags(connection, SEND_USER_CONFIRM_REPLY); + return; + } + + if (connection->authentication_flags & SEND_USER_PASSKEY_REPLY){ + hci_send_cmd(&hci_user_passkey_request_reply, &connection->address, 000000); + connectionClearAuthenticationFlags(connection, SEND_USER_PASSKEY_REPLY); + return; } } - if (!hci_can_send_packet_now(HCI_COMMAND_DATA_PACKET)) return; - switch (hci_stack.state){ case HCI_STATE_INITIALIZING: // log_info("hci_init: substate %u\n", hci_stack.substate); @@ -1337,6 +1356,26 @@ int hci_send_cmd_packet(uint8_t *packet, int size){ return hci_stack.hci_transport->send_packet(HCI_COMMAND_DATA_PACKET, packet, size); } +// Configure Secure Simple Pairing + +// enable will enable SSP during init +void hci_ssp_set_enable(int enable){ + hci_stack.ssp_enable = enable; +} + +// if set, BTstack will respond to io capability request using authentication requirement +void hci_ssp_set_io_capability(int io_capability){ + hci_stack.ssp_io_capability = io_capability; +} +void hci_ssp_set_authentication_requirement(int authentication_requirement){ + hci_stack.ssp_authentication_requirement = authentication_requirement; +} + +// if set, BTstack will confirm a numberic comparion and enter '000000' if requested +void hci_ssp_set_auto_accept(int auto_accept){ + hci_stack.ssp_auto_accept = auto_accept; +} + /** * pre: numcmds >= 0 - it's allowed to send a command to the controller */ diff --git a/src/hci.h b/src/hci.h index b169bab2e..231872716 100644 --- a/src/hci.h +++ b/src/hci.h @@ -196,18 +196,22 @@ extern "C" { * Connection State */ typedef enum { - AUTH_FLAGS_NONE = 0x00, - RECV_LINK_KEY_REQUEST = 0x01, - HANDLE_LINK_KEY_REQUEST = 0x02, - SENT_LINK_KEY_REPLY = 0x04, - SENT_LINK_KEY_NEGATIVE_REQUEST = 0x08, - RECV_LINK_KEY_NOTIFICATION = 0x10, - RECV_PIN_CODE_REQUEST = 0x20, - SENT_PIN_CODE_REPLY = 0x40, - SENT_PIN_CODE_NEGATIVE_REPLY = 0x80, + AUTH_FLAGS_NONE = 0x0000, + RECV_LINK_KEY_REQUEST = 0x0001, + HANDLE_LINK_KEY_REQUEST = 0x0002, + SENT_LINK_KEY_REPLY = 0x0004, + SENT_LINK_KEY_NEGATIVE_REQUEST = 0x0008, + RECV_LINK_KEY_NOTIFICATION = 0x0010, + RECV_PIN_CODE_REQUEST = 0x0020, + SENT_PIN_CODE_REPLY = 0x0040, + SENT_PIN_CODE_NEGATIVE_REPLY = 0x0080, // SSP - RECV_IO_CAPABILITIES_REQUEST = 0x100; - SENT_IO_CAPABILITIES_REPLY = 0x200; + RECV_IO_CAPABILITIES_REQUEST = 0x0100, + SEND_IO_CAPABILITIES_REPLY = 0x0200, + RECV_USER_CONFIRM_REQUEST = 0x0400, + SEND_USER_CONFIRM_REPLY = 0x0800, + RECV_USER_PASSKEY_REQUEST = 0x1000, + SEND_USER_PASSKEY_REPLY = 0x2000, } hci_authentication_flags_t; typedef enum { @@ -378,7 +382,7 @@ int hci_power_control(HCI_POWER_MODE mode); // Allows to control if device is discoverable. OFF by default. void hci_discoverable_control(uint8_t enable); -// Creates and sends hci command packets based on a template and +// Creates and sends HCI command packets based on a template and // a list of parameters. Will return error if outgoing data buffer // is occupied. int hci_send_cmd(const hci_cmd_t *cmd, ...); @@ -386,6 +390,17 @@ int hci_send_cmd(const hci_cmd_t *cmd, ...); // Deletes link key for remote device with baseband address. void hci_drop_link_key_for_bd_addr(bd_addr_t *addr); +// Configure Secure Simple Pairing + +// enable will enable SSP during init +void hci_ssp_set_enable(int enable); + +// if set, BTstack will respond to io capability request using authentication requirement +void hci_ssp_set_io_capability(int ssp_io_capability); +void hci_ssp_set_authentication_requirement(int authentication_requirement); + +// if set, BTstack will confirm a numberic comparion and enter '000000' if requested +void hci_ssp_set_auto_accept(int auto_accept); #if defined __cplusplus }