1*3deb3ec6SMatthias Ringwald /* 2*3deb3ec6SMatthias Ringwald * Copyright (C) 2014 BlueKitchen GmbH 3*3deb3ec6SMatthias Ringwald * 4*3deb3ec6SMatthias Ringwald * Redistribution and use in source and binary forms, with or without 5*3deb3ec6SMatthias Ringwald * modification, are permitted provided that the following conditions 6*3deb3ec6SMatthias Ringwald * are met: 7*3deb3ec6SMatthias Ringwald * 8*3deb3ec6SMatthias Ringwald * 1. Redistributions of source code must retain the above copyright 9*3deb3ec6SMatthias Ringwald * notice, this list of conditions and the following disclaimer. 10*3deb3ec6SMatthias Ringwald * 2. Redistributions in binary form must reproduce the above copyright 11*3deb3ec6SMatthias Ringwald * notice, this list of conditions and the following disclaimer in the 12*3deb3ec6SMatthias Ringwald * documentation and/or other materials provided with the distribution. 13*3deb3ec6SMatthias Ringwald * 3. Neither the name of the copyright holders nor the names of 14*3deb3ec6SMatthias Ringwald * contributors may be used to endorse or promote products derived 15*3deb3ec6SMatthias Ringwald * from this software without specific prior written permission. 16*3deb3ec6SMatthias Ringwald * 4. Any redistribution, use, or modification is done solely for 17*3deb3ec6SMatthias Ringwald * personal benefit and not for any commercial purpose or for 18*3deb3ec6SMatthias Ringwald * monetary gain. 19*3deb3ec6SMatthias Ringwald * 20*3deb3ec6SMatthias Ringwald * THIS SOFTWARE IS PROVIDED BY BLUEKITCHEN GMBH AND CONTRIBUTORS 21*3deb3ec6SMatthias Ringwald * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 22*3deb3ec6SMatthias Ringwald * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS 23*3deb3ec6SMatthias Ringwald * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL MATTHIAS 24*3deb3ec6SMatthias Ringwald * RINGWALD OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, 25*3deb3ec6SMatthias Ringwald * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, 26*3deb3ec6SMatthias Ringwald * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS 27*3deb3ec6SMatthias Ringwald * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED 28*3deb3ec6SMatthias Ringwald * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, 29*3deb3ec6SMatthias Ringwald * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF 30*3deb3ec6SMatthias Ringwald * THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 31*3deb3ec6SMatthias Ringwald * SUCH DAMAGE. 32*3deb3ec6SMatthias Ringwald * 33*3deb3ec6SMatthias Ringwald * Please inquire about commercial licensing options at 34*3deb3ec6SMatthias Ringwald * [email protected] 35*3deb3ec6SMatthias Ringwald * 36*3deb3ec6SMatthias Ringwald */ 37*3deb3ec6SMatthias Ringwald 38*3deb3ec6SMatthias Ringwald #ifndef __SM_H 39*3deb3ec6SMatthias Ringwald #define __SM_H 40*3deb3ec6SMatthias Ringwald 41*3deb3ec6SMatthias Ringwald #include "utils.h" 42*3deb3ec6SMatthias Ringwald #include "btstack.h" 43*3deb3ec6SMatthias Ringwald #include <stdint.h> 44*3deb3ec6SMatthias Ringwald 45*3deb3ec6SMatthias Ringwald #if defined __cplusplus 46*3deb3ec6SMatthias Ringwald extern "C" { 47*3deb3ec6SMatthias Ringwald #endif 48*3deb3ec6SMatthias Ringwald 49*3deb3ec6SMatthias Ringwald 50*3deb3ec6SMatthias Ringwald // Bluetooth Spec definitions 51*3deb3ec6SMatthias Ringwald typedef enum { 52*3deb3ec6SMatthias Ringwald SM_CODE_PAIRING_REQUEST = 0X01, 53*3deb3ec6SMatthias Ringwald SM_CODE_PAIRING_RESPONSE, 54*3deb3ec6SMatthias Ringwald SM_CODE_PAIRING_CONFIRM, 55*3deb3ec6SMatthias Ringwald SM_CODE_PAIRING_RANDOM, 56*3deb3ec6SMatthias Ringwald SM_CODE_PAIRING_FAILED, 57*3deb3ec6SMatthias Ringwald SM_CODE_ENCRYPTION_INFORMATION, 58*3deb3ec6SMatthias Ringwald SM_CODE_MASTER_IDENTIFICATION, 59*3deb3ec6SMatthias Ringwald SM_CODE_IDENTITY_INFORMATION, 60*3deb3ec6SMatthias Ringwald SM_CODE_IDENTITY_ADDRESS_INFORMATION, 61*3deb3ec6SMatthias Ringwald SM_CODE_SIGNING_INFORMATION, 62*3deb3ec6SMatthias Ringwald SM_CODE_SECURITY_REQUEST 63*3deb3ec6SMatthias Ringwald } SECURITY_MANAGER_COMMANDS; 64*3deb3ec6SMatthias Ringwald 65*3deb3ec6SMatthias Ringwald // IO Capability Values 66*3deb3ec6SMatthias Ringwald typedef enum { 67*3deb3ec6SMatthias Ringwald IO_CAPABILITY_DISPLAY_ONLY = 0, 68*3deb3ec6SMatthias Ringwald IO_CAPABILITY_DISPLAY_YES_NO, 69*3deb3ec6SMatthias Ringwald IO_CAPABILITY_KEYBOARD_ONLY, 70*3deb3ec6SMatthias Ringwald IO_CAPABILITY_NO_INPUT_NO_OUTPUT, 71*3deb3ec6SMatthias Ringwald IO_CAPABILITY_KEYBOARD_DISPLAY, // not used by secure simple pairing 72*3deb3ec6SMatthias Ringwald } io_capability_t; 73*3deb3ec6SMatthias Ringwald 74*3deb3ec6SMatthias Ringwald 75*3deb3ec6SMatthias Ringwald // Authentication requirement flags 76*3deb3ec6SMatthias Ringwald #define SM_AUTHREQ_NO_BONDING 0x00 77*3deb3ec6SMatthias Ringwald #define SM_AUTHREQ_BONDING 0x01 78*3deb3ec6SMatthias Ringwald #define SM_AUTHREQ_MITM_PROTECTION 0x04 79*3deb3ec6SMatthias Ringwald 80*3deb3ec6SMatthias Ringwald // Key distribution flags used by spec 81*3deb3ec6SMatthias Ringwald #define SM_KEYDIST_ENC_KEY 0X01 82*3deb3ec6SMatthias Ringwald #define SM_KEYDIST_ID_KEY 0x02 83*3deb3ec6SMatthias Ringwald #define SM_KEYDIST_SIGN 0x04 84*3deb3ec6SMatthias Ringwald 85*3deb3ec6SMatthias Ringwald // Key distribution flags used internally 86*3deb3ec6SMatthias Ringwald #define SM_KEYDIST_FLAG_ENCRYPTION_INFORMATION 0x01 87*3deb3ec6SMatthias Ringwald #define SM_KEYDIST_FLAG_MASTER_IDENTIFICATION 0x02 88*3deb3ec6SMatthias Ringwald #define SM_KEYDIST_FLAG_IDENTITY_INFORMATION 0x04 89*3deb3ec6SMatthias Ringwald #define SM_KEYDIST_FLAG_IDENTITY_ADDRESS_INFORMATION 0x08 90*3deb3ec6SMatthias Ringwald #define SM_KEYDIST_FLAG_SIGNING_IDENTIFICATION 0x10 91*3deb3ec6SMatthias Ringwald 92*3deb3ec6SMatthias Ringwald // STK Generation Methods 93*3deb3ec6SMatthias Ringwald #define SM_STK_GENERATION_METHOD_JUST_WORKS 0x01 94*3deb3ec6SMatthias Ringwald #define SM_STK_GENERATION_METHOD_OOB 0x02 95*3deb3ec6SMatthias Ringwald #define SM_STK_GENERATION_METHOD_PASSKEY 0x04 96*3deb3ec6SMatthias Ringwald 97*3deb3ec6SMatthias Ringwald // Pairing Failed Reasons 98*3deb3ec6SMatthias Ringwald #define SM_REASON_RESERVED 0x00 99*3deb3ec6SMatthias Ringwald #define SM_REASON_PASSKEYT_ENTRY_FAILED 0x01 100*3deb3ec6SMatthias Ringwald #define SM_REASON_OOB_NOT_AVAILABLE 0x02 101*3deb3ec6SMatthias Ringwald #define SM_REASON_AUTHENTHICATION_REQUIREMENTS 0x03 102*3deb3ec6SMatthias Ringwald #define SM_REASON_CONFIRM_VALUE_FAILED 0x04 103*3deb3ec6SMatthias Ringwald #define SM_REASON_PAIRING_NOT_SUPPORTED 0x05 104*3deb3ec6SMatthias Ringwald #define SM_REASON_ENCRYPTION_KEY_SIZE 0x06 105*3deb3ec6SMatthias Ringwald #define SM_REASON_COMMAND_NOT_SUPPORTED 0x07 106*3deb3ec6SMatthias Ringwald #define SM_REASON_UNSPECIFIED_REASON 0x08 107*3deb3ec6SMatthias Ringwald #define SM_REASON_REPEATED_ATTEMPTS 0x09 108*3deb3ec6SMatthias Ringwald // also, invalid parameters 109*3deb3ec6SMatthias Ringwald // and reserved 110*3deb3ec6SMatthias Ringwald 111*3deb3ec6SMatthias Ringwald // Only for PTS testing 112*3deb3ec6SMatthias Ringwald void sm_test_set_irk(sm_key_t irk); 113*3deb3ec6SMatthias Ringwald 114*3deb3ec6SMatthias Ringwald typedef struct { 115*3deb3ec6SMatthias Ringwald linked_item_t item; 116*3deb3ec6SMatthias Ringwald bd_addr_t address; 117*3deb3ec6SMatthias Ringwald bd_addr_type_t address_type; 118*3deb3ec6SMatthias Ringwald } sm_lookup_entry_t; 119*3deb3ec6SMatthias Ringwald 120*3deb3ec6SMatthias Ringwald /* API_START */ 121*3deb3ec6SMatthias Ringwald 122*3deb3ec6SMatthias Ringwald /** 123*3deb3ec6SMatthias Ringwald * @brief Initializes the Security Manager, connects to L2CAP 124*3deb3ec6SMatthias Ringwald */ 125*3deb3ec6SMatthias Ringwald void sm_init(void); 126*3deb3ec6SMatthias Ringwald 127*3deb3ec6SMatthias Ringwald /** 128*3deb3ec6SMatthias Ringwald * @brief Set secret ER key for key generation as described in Core V4.0, Vol 3, Part G, 5.2.2 129*3deb3ec6SMatthias Ringwald * @param er 130*3deb3ec6SMatthias Ringwald */ 131*3deb3ec6SMatthias Ringwald void sm_set_er(sm_key_t er); 132*3deb3ec6SMatthias Ringwald 133*3deb3ec6SMatthias Ringwald /** 134*3deb3ec6SMatthias Ringwald * @brief Set secret IR key for key generation as described in Core V4.0, Vol 3, Part G, 5.2.2 135*3deb3ec6SMatthias Ringwald */ 136*3deb3ec6SMatthias Ringwald void sm_set_ir(sm_key_t ir); 137*3deb3ec6SMatthias Ringwald 138*3deb3ec6SMatthias Ringwald /** 139*3deb3ec6SMatthias Ringwald * 140*3deb3ec6SMatthias Ringwald * @brief Registers OOB Data Callback. The callback should set the oob_data and return 1 if OOB data is availble 141*3deb3ec6SMatthias Ringwald * @param get_oob_data_callback 142*3deb3ec6SMatthias Ringwald */ 143*3deb3ec6SMatthias Ringwald void sm_register_oob_data_callback( int (*get_oob_data_callback)(uint8_t addres_type, bd_addr_t addr, uint8_t * oob_data)); 144*3deb3ec6SMatthias Ringwald 145*3deb3ec6SMatthias Ringwald /** 146*3deb3ec6SMatthias Ringwald * 147*3deb3ec6SMatthias Ringwald * @brief Registers packet handler. Called by att_server.c 148*3deb3ec6SMatthias Ringwald */ 149*3deb3ec6SMatthias Ringwald void sm_register_packet_handler(btstack_packet_handler_t handler); 150*3deb3ec6SMatthias Ringwald 151*3deb3ec6SMatthias Ringwald /** 152*3deb3ec6SMatthias Ringwald * @brief Limit the STK generation methods. Bonding is stopped if the resulting one isn't in the list 153*3deb3ec6SMatthias Ringwald * @param OR combination of SM_STK_GENERATION_METHOD_ 154*3deb3ec6SMatthias Ringwald */ 155*3deb3ec6SMatthias Ringwald void sm_set_accepted_stk_generation_methods(uint8_t accepted_stk_generation_methods); 156*3deb3ec6SMatthias Ringwald 157*3deb3ec6SMatthias Ringwald /** 158*3deb3ec6SMatthias Ringwald * @brief Set the accepted encryption key size range. Bonding is stopped if the result isn't within the range 159*3deb3ec6SMatthias Ringwald * @param min_size (default 7) 160*3deb3ec6SMatthias Ringwald * @param max_size (default 16) 161*3deb3ec6SMatthias Ringwald */ 162*3deb3ec6SMatthias Ringwald void sm_set_encryption_key_size_range(uint8_t min_size, uint8_t max_size); 163*3deb3ec6SMatthias Ringwald 164*3deb3ec6SMatthias Ringwald /** 165*3deb3ec6SMatthias Ringwald * @brief Sets the requested authentication requirements, bonding yes/no, MITM yes/no 166*3deb3ec6SMatthias Ringwald * @param OR combination of SM_AUTHREQ_ flags 167*3deb3ec6SMatthias Ringwald */ 168*3deb3ec6SMatthias Ringwald void sm_set_authentication_requirements(uint8_t auth_req); 169*3deb3ec6SMatthias Ringwald 170*3deb3ec6SMatthias Ringwald /** 171*3deb3ec6SMatthias Ringwald * @brief Sets the available IO Capabilities 172*3deb3ec6SMatthias Ringwald * @param IO_CAPABILITY_ 173*3deb3ec6SMatthias Ringwald */ 174*3deb3ec6SMatthias Ringwald void sm_set_io_capabilities(io_capability_t io_capability); 175*3deb3ec6SMatthias Ringwald 176*3deb3ec6SMatthias Ringwald /** 177*3deb3ec6SMatthias Ringwald * @brief Let Peripheral request an encrypted connection right after connecting 178*3deb3ec6SMatthias Ringwald * @note Not used normally. Bonding is triggered by access to protected attributes in ATT Server 179*3deb3ec6SMatthias Ringwald */ 180*3deb3ec6SMatthias Ringwald void sm_set_request_security(int enable); 181*3deb3ec6SMatthias Ringwald 182*3deb3ec6SMatthias Ringwald /** 183*3deb3ec6SMatthias Ringwald * @brief Trigger Security Request 184*3deb3ec6SMatthias Ringwald * @note Not used normally. Bonding is triggered by access to protected attributes in ATT Server 185*3deb3ec6SMatthias Ringwald */ 186*3deb3ec6SMatthias Ringwald void sm_send_security_request(uint16_t handle); 187*3deb3ec6SMatthias Ringwald 188*3deb3ec6SMatthias Ringwald /** 189*3deb3ec6SMatthias Ringwald * @brief Decline bonding triggered by event before 190*3deb3ec6SMatthias Ringwald * @param addr_type and address 191*3deb3ec6SMatthias Ringwald */ 192*3deb3ec6SMatthias Ringwald void sm_bonding_decline(uint16_t handle); 193*3deb3ec6SMatthias Ringwald 194*3deb3ec6SMatthias Ringwald /** 195*3deb3ec6SMatthias Ringwald * @brief Confirm Just Works bonding 196*3deb3ec6SMatthias Ringwald * @param addr_type and address 197*3deb3ec6SMatthias Ringwald */ 198*3deb3ec6SMatthias Ringwald void sm_just_works_confirm(uint16_t handle); 199*3deb3ec6SMatthias Ringwald 200*3deb3ec6SMatthias Ringwald /** 201*3deb3ec6SMatthias Ringwald * @brief Reports passkey input by user 202*3deb3ec6SMatthias Ringwald * @param addr_type and address 203*3deb3ec6SMatthias Ringwald * @param passkey in [0..999999] 204*3deb3ec6SMatthias Ringwald */ 205*3deb3ec6SMatthias Ringwald void sm_passkey_input(uint16_t handle, uint32_t passkey); 206*3deb3ec6SMatthias Ringwald 207*3deb3ec6SMatthias Ringwald /** 208*3deb3ec6SMatthias Ringwald * 209*3deb3ec6SMatthias Ringwald * @brief Get encryption key size. 210*3deb3ec6SMatthias Ringwald * @param addr_type and address 211*3deb3ec6SMatthias Ringwald * @return 0 if not encrypted, 7-16 otherwise 212*3deb3ec6SMatthias Ringwald */ 213*3deb3ec6SMatthias Ringwald int sm_encryption_key_size(uint16_t handle); 214*3deb3ec6SMatthias Ringwald 215*3deb3ec6SMatthias Ringwald /** 216*3deb3ec6SMatthias Ringwald * @brief Get authentication property. 217*3deb3ec6SMatthias Ringwald * @param addr_type and address 218*3deb3ec6SMatthias Ringwald * @return 1 if bonded with OOB/Passkey (AND MITM protection) 219*3deb3ec6SMatthias Ringwald */ 220*3deb3ec6SMatthias Ringwald int sm_authenticated(uint16_t handle); 221*3deb3ec6SMatthias Ringwald 222*3deb3ec6SMatthias Ringwald /** 223*3deb3ec6SMatthias Ringwald * @brief Queries authorization state. 224*3deb3ec6SMatthias Ringwald * @param addr_type and address 225*3deb3ec6SMatthias Ringwald * @return authorization_state for the current session 226*3deb3ec6SMatthias Ringwald */ 227*3deb3ec6SMatthias Ringwald authorization_state_t sm_authorization_state(uint16_t handle); 228*3deb3ec6SMatthias Ringwald 229*3deb3ec6SMatthias Ringwald /** 230*3deb3ec6SMatthias Ringwald * @brief Used by att_server.c to request user authorization. 231*3deb3ec6SMatthias Ringwald * @param addr_type and address 232*3deb3ec6SMatthias Ringwald */ 233*3deb3ec6SMatthias Ringwald void sm_request_pairing(uint16_t handle); 234*3deb3ec6SMatthias Ringwald 235*3deb3ec6SMatthias Ringwald /** 236*3deb3ec6SMatthias Ringwald * @brief Report user authorization decline. 237*3deb3ec6SMatthias Ringwald * @param addr_type and address 238*3deb3ec6SMatthias Ringwald */ 239*3deb3ec6SMatthias Ringwald void sm_authorization_decline(uint16_t handle); 240*3deb3ec6SMatthias Ringwald 241*3deb3ec6SMatthias Ringwald /** 242*3deb3ec6SMatthias Ringwald * @brief Report user authorization grant. 243*3deb3ec6SMatthias Ringwald * @param addr_type and address 244*3deb3ec6SMatthias Ringwald */ 245*3deb3ec6SMatthias Ringwald void sm_authorization_grant(uint16_t handle); 246*3deb3ec6SMatthias Ringwald 247*3deb3ec6SMatthias Ringwald /** 248*3deb3ec6SMatthias Ringwald * @brief Support for signed writes, used by att_server. 249*3deb3ec6SMatthias Ringwald * @note Message and result are in little endian to allows passing in ATT PDU without flipping. 250*3deb3ec6SMatthias Ringwald * @note calculated hash in done_callback is big endian 251*3deb3ec6SMatthias Ringwald */ 252*3deb3ec6SMatthias Ringwald int sm_cmac_ready(void); 253*3deb3ec6SMatthias Ringwald void sm_cmac_start(sm_key_t k, uint8_t opcode, uint16_t attribute_handle, uint16_t message_len, uint8_t * message, uint32_t sign_counter, void (*done_handler)(uint8_t hash[8])); 254*3deb3ec6SMatthias Ringwald 255*3deb3ec6SMatthias Ringwald /* 256*3deb3ec6SMatthias Ringwald * @brief Match address against bonded devices 257*3deb3ec6SMatthias Ringwald * @return 0 if successfully added to lookup queue 258*3deb3ec6SMatthias Ringwald * @note Triggers SM_IDENTITY_RESOLVING_* events 259*3deb3ec6SMatthias Ringwald */ 260*3deb3ec6SMatthias Ringwald int sm_address_resolution_lookup(uint8_t addr_type, bd_addr_t addr); 261*3deb3ec6SMatthias Ringwald 262*3deb3ec6SMatthias Ringwald /** 263*3deb3ec6SMatthias Ringwald * @brief Identify device in LE Device DB. 264*3deb3ec6SMatthias Ringwald * @param handle 265*3deb3ec6SMatthias Ringwald * @return index from le_device_db or -1 if not found/identified 266*3deb3ec6SMatthias Ringwald */ 267*3deb3ec6SMatthias Ringwald int sm_le_device_index(uint16_t handle ); 268*3deb3ec6SMatthias Ringwald /* API_END */ 269*3deb3ec6SMatthias Ringwald 270*3deb3ec6SMatthias Ringwald // testing only 271*3deb3ec6SMatthias Ringwald void sm_test_use_fixed_local_csrk(void); 272*3deb3ec6SMatthias Ringwald 273*3deb3ec6SMatthias Ringwald #if defined __cplusplus 274*3deb3ec6SMatthias Ringwald } 275*3deb3ec6SMatthias Ringwald #endif 276*3deb3ec6SMatthias Ringwald 277*3deb3ec6SMatthias Ringwald #endif // __SM_H 278