int btd_event_request_pin(bdaddr_t *sba, bdaddr_t *dba, gboolean secure) { struct btd_adapter *adapter; struct btd_device *device; char pin[17]; ssize_t pinlen; gboolean display = FALSE; if (!get_adapter_and_device(sba, dba, &adapter, &device, TRUE)) return -ENODEV; memset(pin, 0, sizeof(pin)); pinlen = btd_adapter_get_pin(adapter, device, pin, &display); if (pinlen > 0 && (!secure || pinlen == 16)) { if (display && device_is_bonding(device, NULL)) return device_request_authentication(device, AUTH_TYPE_NOTIFY_PINCODE, pin, secure, pincode_cb); btd_adapter_pincode_reply(adapter, dba, pin, pinlen); return 0; } return device_request_authentication(device, AUTH_TYPE_PINCODE, NULL, secure, pincode_cb); }
int btd_event_request_pin(bdaddr_t *sba, bdaddr_t *dba) { struct btd_adapter *adapter; struct btd_device *device; char pin[17]; int pinlen; if (!get_adapter_and_device(sba, dba, &adapter, &device, TRUE)) return -ENODEV; /* Check if the adapter is not pairable and if there isn't a bonding in * progress */ if (!adapter_is_pairable(adapter) && !device_is_bonding(device, NULL)) return -EPERM; memset(pin, 0, sizeof(pin)); pinlen = read_pin_code(sba, dba, pin); if (pinlen > 0) { btd_adapter_pincode_reply(adapter, dba, pin); return 0; } return device_request_authentication(device, AUTH_TYPE_PINCODE, 0, pincode_cb); }
int btd_event_user_confirm(bdaddr_t *sba, bdaddr_t *dba, uint32_t passkey) { struct btd_adapter *adapter; struct btd_device *device; struct agent *agent; uint8_t rem_cap, rem_auth, loc_cap, loc_auth; gboolean bonding_initiator; if (!get_adapter_and_device(sba, dba, &adapter, &device, TRUE)) return -ENODEV; if (btd_adapter_get_auth_info(adapter, dba, &loc_auth) < 0) { error("Unable to get local authentication requirements"); goto fail; } agent = device_get_agent(device); if (agent == NULL) { error("No agent available for user confirmation"); goto fail; } loc_cap = agent_get_io_capability(agent); DBG("confirm IO capabilities are 0x%02x", loc_cap); DBG("confirm authentication requirement is 0x%02x", loc_auth); rem_cap = device_get_cap(device); rem_auth = device_get_auth(device); DBG("remote IO capabilities are 0x%02x", rem_cap); DBG("remote authentication requirement is 0x%02x", rem_auth); /* If we require MITM but the remote device can't provide that * (it has NoInputNoOutput) then reject the confirmation * request. The only exception is when we're dedicated bonding * initiators since then we always have the MITM bit set. */ bonding_initiator = device_is_bonding(device, NULL); if (!bonding_initiator && (loc_auth & 0x01) && rem_cap == 0x03) { error("Rejecting request: remote device can't provide MITM"); goto fail; } /* If no side requires MITM protection; auto-accept */ if ((loc_auth == 0xff || !(loc_auth & 0x01) || rem_cap == 0x03) && (!(rem_auth & 0x01) || loc_cap == 0x03)) { DBG("auto accept of confirmation"); /* Wait 5 milliseconds before doing auto-accept */ usleep(5000); if (confirm_reply(adapter, device, TRUE) < 0) return -EIO; return device_request_authentication(device, AUTH_TYPE_AUTO, 0, NULL); } return device_request_authentication(device, AUTH_TYPE_CONFIRM, passkey, confirm_cb); fail: return confirm_reply(adapter, device, FALSE); }