summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorSudha Bheemanna <b.sudha@samsung.com>2016-08-25 12:46:07 +0530
committerSeung-Woo Kim <sw0312.kim@samsung.com>2016-09-24 14:37:46 +0900
commit8c6f9d56ed82d9287086739993bd2e7c347cb28b (patch)
treead99cbcc7a50533efdf0f01ef0db3c6de06cb68f
parent5865861d9e77d6c32d8619cc583201db2acf61a2 (diff)
downloadlinux-exynos-8c6f9d56ed82d9287086739993bd2e7c347cb28b.tar.gz
linux-exynos-8c6f9d56ed82d9287086739993bd2e7c347cb28b.tar.bz2
linux-exynos-8c6f9d56ed82d9287086739993bd2e7c347cb28b.zip
Added new MGMT command to set LE scan parameters Change-Id: I5ea660f97e93dfcc72273971ad0250e7f582f718 Signed-off-by: Sudha Bheemanna <b.sudha@samsung.com>
-rw-r--r--include/net/bluetooth/mgmt_tizen.h8
-rw-r--r--net/bluetooth/mgmt.c59
2 files changed, 67 insertions, 0 deletions
diff --git a/include/net/bluetooth/mgmt_tizen.h b/include/net/bluetooth/mgmt_tizen.h
index 4f24c42132b2..4c2e9d0c54d6 100644
--- a/include/net/bluetooth/mgmt_tizen.h
+++ b/include/net/bluetooth/mgmt_tizen.h
@@ -143,6 +143,14 @@ struct mgmt_cp_set_manufacturer_data {
#define MGMT_SET_MANUFACTURER_DATA_SIZE 100
/* Set Manufacturer Data */
+#define MGMT_OP_LE_SET_SCAN_PARAMS (TIZEN_OP_CODE_BASE + 0x0f)
+struct mgmt_cp_le_set_scan_params {
+ __u8 type; /* le scan type */
+ __le16 interval;
+ __le16 window;
+} __packed;
+#define MGMT_LE_SET_SCAN_PARAMS_SIZE 5
+
/* EVENTS */
/* For device name update changes */
diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c
index 2db1d2067c89..194511e828eb 100644
--- a/net/bluetooth/mgmt.c
+++ b/net/bluetooth/mgmt.c
@@ -7103,6 +7103,64 @@ failed:
hci_dev_unlock(hdev);
return err;
}
+
+static int le_set_scan_params(struct sock *sk, struct hci_dev *hdev,
+ void *data, u16 len)
+{
+ struct mgmt_cp_le_set_scan_params *cp = data;
+ __u16 interval, window;
+ int err;
+
+ BT_DBG("%s", hdev->name);
+
+ if (!lmp_le_capable(hdev))
+ return mgmt_cmd_status(sk, hdev->id, MGMT_OP_LE_SET_SCAN_PARAMS,
+ MGMT_STATUS_NOT_SUPPORTED);
+
+ interval = __le16_to_cpu(cp->interval);
+
+ if (interval < 0x0004 || interval > 0x4000)
+ return mgmt_cmd_status(sk, hdev->id, MGMT_OP_LE_SET_SCAN_PARAMS,
+ MGMT_STATUS_INVALID_PARAMS);
+
+ window = __le16_to_cpu(cp->window);
+
+ if (window < 0x0004 || window > 0x4000)
+ return mgmt_cmd_status(sk, hdev->id, MGMT_OP_LE_SET_SCAN_PARAMS,
+ MGMT_STATUS_INVALID_PARAMS);
+
+ if (window > interval)
+ return mgmt_cmd_status(sk, hdev->id, MGMT_OP_LE_SET_SCAN_PARAMS,
+ MGMT_STATUS_INVALID_PARAMS);
+
+ hci_dev_lock(hdev);
+
+ hdev->le_scan_type = cp->type;
+ hdev->le_scan_interval = interval;
+ hdev->le_scan_window = window;
+
+ err = mgmt_cmd_complete(sk, hdev->id, MGMT_OP_LE_SET_SCAN_PARAMS, 0,
+ NULL, 0);
+
+ /* If background scan is running, restart it so new parameters are
+ * loaded.
+ */
+ if (hci_dev_test_flag(hdev, HCI_LE_SCAN) &&
+ hdev->discovery.state == DISCOVERY_STOPPED) {
+ struct hci_request req;
+
+ hci_req_init(&req, hdev);
+
+ hci_req_add_le_scan_disable(&req);
+ hci_req_add_le_passive_scan(&req);
+
+ hci_req_run(&req, NULL);
+ }
+
+ hci_dev_unlock(hdev);
+
+ return err;
+}
#endif /* TIZEN_BT */
static bool ltk_is_valid(struct mgmt_ltk_info *key)
@@ -8948,6 +9006,7 @@ static const struct hci_mgmt_handler tizen_mgmt_handlers[] = {
{ disable_le_auto_connect, MGMT_DISABLE_LE_AUTO_CONNECT_SIZE },
{ le_conn_update, MGMT_LE_CONN_UPDATE_SIZE },
{ set_manufacturer_data, MGMT_SET_MANUFACTURER_DATA_SIZE },
+ { le_set_scan_params, MGMT_LE_SET_SCAN_PARAMS_SIZE },
};
#endif