diff options
author | Johan Hedberg <johan.hedberg@intel.com> | 2011-11-07 16:13:38 -0500 |
---|---|---|
committer | Gustavo F. Padovan <padovan@profusion.mobi> | 2011-11-08 10:03:25 -0500 |
commit | 86742e1eca319069490f6f20c2892baafc2a6922 (patch) | |
tree | 4274953eb153f00aaa600d46ca587dc2395a8ff8 /net/bluetooth | |
parent | bd2d1334e1dd64765b29f9e1b592777c410ed121 (diff) |
Bluetooth: Update link key mgmt APIs to match latest spec.
BR/EDR link keys have their own commands and events (separate from SMP)
and the remove_keys command (previously remove_key) removes keys of any
kind for the specified remote address.
Signed-off-by: Johan Hedberg <johan.hedberg@intel.com>
Signed-off-by: Gustavo F. Padovan <padovan@profusion.mobi>
Diffstat (limited to 'net/bluetooth')
-rw-r--r-- | net/bluetooth/hci_core.c | 4 | ||||
-rw-r--r-- | net/bluetooth/mgmt.c | 43 |
2 files changed, 25 insertions, 22 deletions
diff --git a/net/bluetooth/hci_core.c b/net/bluetooth/hci_core.c index e4ddf36d1701..693c0dfc6b9d 100644 --- a/net/bluetooth/hci_core.c +++ b/net/bluetooth/hci_core.c | |||
@@ -1140,7 +1140,7 @@ int hci_add_link_key(struct hci_dev *hdev, struct hci_conn *conn, int new_key, | |||
1140 | 1140 | ||
1141 | persistent = hci_persistent_key(hdev, conn, type, old_key_type); | 1141 | persistent = hci_persistent_key(hdev, conn, type, old_key_type); |
1142 | 1142 | ||
1143 | mgmt_new_key(hdev->id, key, persistent); | 1143 | mgmt_new_link_key(hdev->id, key, persistent); |
1144 | 1144 | ||
1145 | if (!persistent) { | 1145 | if (!persistent) { |
1146 | list_del(&key->list); | 1146 | list_del(&key->list); |
@@ -1183,7 +1183,7 @@ int hci_add_ltk(struct hci_dev *hdev, int new_key, bdaddr_t *bdaddr, | |||
1183 | memcpy(id->rand, rand, sizeof(id->rand)); | 1183 | memcpy(id->rand, rand, sizeof(id->rand)); |
1184 | 1184 | ||
1185 | if (new_key) | 1185 | if (new_key) |
1186 | mgmt_new_key(hdev->id, key, old_key_type); | 1186 | mgmt_new_link_key(hdev->id, key, old_key_type); |
1187 | 1187 | ||
1188 | return 0; | 1188 | return 0; |
1189 | } | 1189 | } |
diff --git a/net/bluetooth/mgmt.c b/net/bluetooth/mgmt.c index af077abdfa98..1939053c3fcd 100644 --- a/net/bluetooth/mgmt.c +++ b/net/bluetooth/mgmt.c | |||
@@ -908,30 +908,32 @@ static int set_service_cache(struct sock *sk, u16 index, unsigned char *data, | |||
908 | return err; | 908 | return err; |
909 | } | 909 | } |
910 | 910 | ||
911 | static int load_keys(struct sock *sk, u16 index, unsigned char *data, u16 len) | 911 | static int load_link_keys(struct sock *sk, u16 index, unsigned char *data, |
912 | u16 len) | ||
912 | { | 913 | { |
913 | struct hci_dev *hdev; | 914 | struct hci_dev *hdev; |
914 | struct mgmt_cp_load_keys *cp; | 915 | struct mgmt_cp_load_link_keys *cp; |
915 | u16 key_count, expected_len; | 916 | u16 key_count, expected_len; |
916 | int i; | 917 | int i; |
917 | 918 | ||
918 | cp = (void *) data; | 919 | cp = (void *) data; |
919 | 920 | ||
920 | if (len < sizeof(*cp)) | 921 | if (len < sizeof(*cp)) |
921 | return cmd_status(sk, index, MGMT_OP_LOAD_KEYS, EINVAL); | 922 | return cmd_status(sk, index, MGMT_OP_LOAD_LINK_KEYS, EINVAL); |
922 | 923 | ||
923 | key_count = get_unaligned_le16(&cp->key_count); | 924 | key_count = get_unaligned_le16(&cp->key_count); |
924 | 925 | ||
925 | expected_len = sizeof(*cp) + key_count * sizeof(struct mgmt_key_info); | 926 | expected_len = sizeof(*cp) + key_count * |
927 | sizeof(struct mgmt_link_key_info); | ||
926 | if (expected_len != len) { | 928 | if (expected_len != len) { |
927 | BT_ERR("load_keys: expected %u bytes, got %u bytes", | 929 | BT_ERR("load_link_keys: expected %u bytes, got %u bytes", |
928 | len, expected_len); | 930 | len, expected_len); |
929 | return cmd_status(sk, index, MGMT_OP_LOAD_KEYS, EINVAL); | 931 | return cmd_status(sk, index, MGMT_OP_LOAD_LINK_KEYS, EINVAL); |
930 | } | 932 | } |
931 | 933 | ||
932 | hdev = hci_dev_get(index); | 934 | hdev = hci_dev_get(index); |
933 | if (!hdev) | 935 | if (!hdev) |
934 | return cmd_status(sk, index, MGMT_OP_LOAD_KEYS, ENODEV); | 936 | return cmd_status(sk, index, MGMT_OP_LOAD_LINK_KEYS, ENODEV); |
935 | 937 | ||
936 | BT_DBG("hci%u debug_keys %u key_count %u", index, cp->debug_keys, | 938 | BT_DBG("hci%u debug_keys %u key_count %u", index, cp->debug_keys, |
937 | key_count); | 939 | key_count); |
@@ -948,7 +950,7 @@ static int load_keys(struct sock *sk, u16 index, unsigned char *data, u16 len) | |||
948 | clear_bit(HCI_DEBUG_KEYS, &hdev->flags); | 950 | clear_bit(HCI_DEBUG_KEYS, &hdev->flags); |
949 | 951 | ||
950 | for (i = 0; i < key_count; i++) { | 952 | for (i = 0; i < key_count; i++) { |
951 | struct mgmt_key_info *key = &cp->keys[i]; | 953 | struct mgmt_link_key_info *key = &cp->keys[i]; |
952 | 954 | ||
953 | hci_add_link_key(hdev, NULL, 0, &key->bdaddr, key->val, key->type, | 955 | hci_add_link_key(hdev, NULL, 0, &key->bdaddr, key->val, key->type, |
954 | key->pin_len); | 956 | key->pin_len); |
@@ -960,27 +962,28 @@ static int load_keys(struct sock *sk, u16 index, unsigned char *data, u16 len) | |||
960 | return 0; | 962 | return 0; |
961 | } | 963 | } |
962 | 964 | ||
963 | static int remove_key(struct sock *sk, u16 index, unsigned char *data, u16 len) | 965 | static int remove_keys(struct sock *sk, u16 index, unsigned char *data, |
966 | u16 len) | ||
964 | { | 967 | { |
965 | struct hci_dev *hdev; | 968 | struct hci_dev *hdev; |
966 | struct mgmt_cp_remove_key *cp; | 969 | struct mgmt_cp_remove_keys *cp; |
967 | struct hci_conn *conn; | 970 | struct hci_conn *conn; |
968 | int err; | 971 | int err; |
969 | 972 | ||
970 | cp = (void *) data; | 973 | cp = (void *) data; |
971 | 974 | ||
972 | if (len != sizeof(*cp)) | 975 | if (len != sizeof(*cp)) |
973 | return cmd_status(sk, index, MGMT_OP_REMOVE_KEY, EINVAL); | 976 | return cmd_status(sk, index, MGMT_OP_REMOVE_KEYS, EINVAL); |
974 | 977 | ||
975 | hdev = hci_dev_get(index); | 978 | hdev = hci_dev_get(index); |
976 | if (!hdev) | 979 | if (!hdev) |
977 | return cmd_status(sk, index, MGMT_OP_REMOVE_KEY, ENODEV); | 980 | return cmd_status(sk, index, MGMT_OP_REMOVE_KEYS, ENODEV); |
978 | 981 | ||
979 | hci_dev_lock_bh(hdev); | 982 | hci_dev_lock_bh(hdev); |
980 | 983 | ||
981 | err = hci_remove_link_key(hdev, &cp->bdaddr); | 984 | err = hci_remove_link_key(hdev, &cp->bdaddr); |
982 | if (err < 0) { | 985 | if (err < 0) { |
983 | err = cmd_status(sk, index, MGMT_OP_REMOVE_KEY, -err); | 986 | err = cmd_status(sk, index, MGMT_OP_REMOVE_KEYS, -err); |
984 | goto unlock; | 987 | goto unlock; |
985 | } | 988 | } |
986 | 989 | ||
@@ -1860,11 +1863,11 @@ int mgmt_control(struct sock *sk, struct msghdr *msg, size_t msglen) | |||
1860 | case MGMT_OP_SET_SERVICE_CACHE: | 1863 | case MGMT_OP_SET_SERVICE_CACHE: |
1861 | err = set_service_cache(sk, index, buf + sizeof(*hdr), len); | 1864 | err = set_service_cache(sk, index, buf + sizeof(*hdr), len); |
1862 | break; | 1865 | break; |
1863 | case MGMT_OP_LOAD_KEYS: | 1866 | case MGMT_OP_LOAD_LINK_KEYS: |
1864 | err = load_keys(sk, index, buf + sizeof(*hdr), len); | 1867 | err = load_link_keys(sk, index, buf + sizeof(*hdr), len); |
1865 | break; | 1868 | break; |
1866 | case MGMT_OP_REMOVE_KEY: | 1869 | case MGMT_OP_REMOVE_KEYS: |
1867 | err = remove_key(sk, index, buf + sizeof(*hdr), len); | 1870 | err = remove_keys(sk, index, buf + sizeof(*hdr), len); |
1868 | break; | 1871 | break; |
1869 | case MGMT_OP_DISCONNECT: | 1872 | case MGMT_OP_DISCONNECT: |
1870 | err = disconnect(sk, index, buf + sizeof(*hdr), len); | 1873 | err = disconnect(sk, index, buf + sizeof(*hdr), len); |
@@ -2055,9 +2058,9 @@ int mgmt_write_scan_failed(u16 index, u8 scan, u8 status) | |||
2055 | return 0; | 2058 | return 0; |
2056 | } | 2059 | } |
2057 | 2060 | ||
2058 | int mgmt_new_key(u16 index, struct link_key *key, u8 persistent) | 2061 | int mgmt_new_link_key(u16 index, struct link_key *key, u8 persistent) |
2059 | { | 2062 | { |
2060 | struct mgmt_ev_new_key ev; | 2063 | struct mgmt_ev_new_link_key ev; |
2061 | 2064 | ||
2062 | memset(&ev, 0, sizeof(ev)); | 2065 | memset(&ev, 0, sizeof(ev)); |
2063 | 2066 | ||
@@ -2067,7 +2070,7 @@ int mgmt_new_key(u16 index, struct link_key *key, u8 persistent) | |||
2067 | memcpy(ev.key.val, key->val, 16); | 2070 | memcpy(ev.key.val, key->val, 16); |
2068 | ev.key.pin_len = key->pin_len; | 2071 | ev.key.pin_len = key->pin_len; |
2069 | 2072 | ||
2070 | return mgmt_event(MGMT_EV_NEW_KEY, index, &ev, sizeof(ev), NULL); | 2073 | return mgmt_event(MGMT_EV_NEW_LINK_KEY, index, &ev, sizeof(ev), NULL); |
2071 | } | 2074 | } |
2072 | 2075 | ||
2073 | int mgmt_connected(u16 index, bdaddr_t *bdaddr, u8 link_type) | 2076 | int mgmt_connected(u16 index, bdaddr_t *bdaddr, u8 link_type) |