Commit 278d933e authored by Brian Gix's avatar Brian Gix Committed by Luiz Augusto von Dentz
Browse files

Bluetooth: Normalize HCI_OP_READ_ENC_KEY_SIZE cmdcmplt



The HCI_OP_READ_ENC_KEY_SIZE command is converted from using the
deprecated hci_request mechanism to use hci_send_cmd, with an
accompanying hci_cc_read_enc_key_size to handle it's return response.

Signed-off-by: default avatarBrian Gix <brian.gix@intel.com>
Signed-off-by: default avatarLuiz Augusto von Dentz <luiz.von.dentz@intel.com>
parent b8288548
Loading
Loading
Loading
Loading
+45 −47
Original line number Diff line number Diff line
@@ -712,6 +712,47 @@ static u8 hci_cc_read_local_version(struct hci_dev *hdev, void *data,
	return rp->status;
}

static u8 hci_cc_read_enc_key_size(struct hci_dev *hdev, void *data,
				   struct sk_buff *skb)
{
	struct hci_rp_read_enc_key_size *rp = data;
	struct hci_conn *conn;
	u16 handle;
	u8 status = rp->status;

	bt_dev_dbg(hdev, "status 0x%2.2x", status);

	handle = le16_to_cpu(rp->handle);

	hci_dev_lock(hdev);

	conn = hci_conn_hash_lookup_handle(hdev, handle);
	if (!conn) {
		status = 0xFF;
		goto done;
	}

	/* While unexpected, the read_enc_key_size command may fail. The most
	 * secure approach is to then assume the key size is 0 to force a
	 * disconnection.
	 */
	if (status) {
		bt_dev_err(hdev, "failed to read key size for handle %u",
			   handle);
		conn->enc_key_size = 0;
	} else {
		conn->enc_key_size = rp->key_size;
		status = 0;
	}

	hci_encrypt_cfm(conn, 0);

done:
	hci_dev_unlock(hdev);

	return status;
}

static u8 hci_cc_read_local_commands(struct hci_dev *hdev, void *data,
				     struct sk_buff *skb)
{
@@ -3534,47 +3575,6 @@ static void hci_remote_name_evt(struct hci_dev *hdev, void *data,
	hci_dev_unlock(hdev);
}

static void read_enc_key_size_complete(struct hci_dev *hdev, u8 status,
				       u16 opcode, struct sk_buff *skb)
{
	const struct hci_rp_read_enc_key_size *rp;
	struct hci_conn *conn;
	u16 handle;

	BT_DBG("%s status 0x%02x", hdev->name, status);

	if (!skb || skb->len < sizeof(*rp)) {
		bt_dev_err(hdev, "invalid read key size response");
		return;
	}

	rp = (void *)skb->data;
	handle = le16_to_cpu(rp->handle);

	hci_dev_lock(hdev);

	conn = hci_conn_hash_lookup_handle(hdev, handle);
	if (!conn)
		goto unlock;

	/* While unexpected, the read_enc_key_size command may fail. The most
	 * secure approach is to then assume the key size is 0 to force a
	 * disconnection.
	 */
	if (rp->status) {
		bt_dev_err(hdev, "failed to read key size for handle %u",
			   handle);
		conn->enc_key_size = 0;
	} else {
		conn->enc_key_size = rp->key_size;
	}

	hci_encrypt_cfm(conn, 0);

unlock:
	hci_dev_unlock(hdev);
}

static void hci_encrypt_change_evt(struct hci_dev *hdev, void *data,
				   struct sk_buff *skb)
{
@@ -3639,7 +3639,6 @@ static void hci_encrypt_change_evt(struct hci_dev *hdev, void *data,
	/* Try reading the encryption key size for encrypted ACL links */
	if (!ev->status && ev->encrypt && conn->type == ACL_LINK) {
		struct hci_cp_read_enc_key_size cp;
		struct hci_request req;

		/* Only send HCI_Read_Encryption_Key_Size if the
		 * controller really supports it. If it doesn't, assume
@@ -3650,12 +3649,9 @@ static void hci_encrypt_change_evt(struct hci_dev *hdev, void *data,
			goto notify;
		}

		hci_req_init(&req, hdev);

		cp.handle = cpu_to_le16(conn->handle);
		hci_req_add(&req, HCI_OP_READ_ENC_KEY_SIZE, sizeof(cp), &cp);

		if (hci_req_run_skb(&req, read_enc_key_size_complete)) {
		if (hci_send_cmd(hdev, HCI_OP_READ_ENC_KEY_SIZE,
				 sizeof(cp), &cp)) {
			bt_dev_err(hdev, "sending read key size failed");
			conn->enc_key_size = HCI_LINK_KEY_SIZE;
			goto notify;
@@ -4037,6 +4033,8 @@ static const struct hci_cc {
	       sizeof(struct hci_rp_read_local_amp_info)),
	HCI_CC(HCI_OP_READ_CLOCK, hci_cc_read_clock,
	       sizeof(struct hci_rp_read_clock)),
	HCI_CC(HCI_OP_READ_ENC_KEY_SIZE, hci_cc_read_enc_key_size,
	       sizeof(struct hci_rp_read_enc_key_size)),
	HCI_CC(HCI_OP_READ_INQ_RSP_TX_POWER, hci_cc_read_inq_rsp_tx_power,
	       sizeof(struct hci_rp_read_inq_rsp_tx_power)),
	HCI_CC(HCI_OP_READ_DEF_ERR_DATA_REPORTING,