From: Michał 'Khorne' Lowas-Rzechonek <michal@xxxxxxxxxxxxx> This patch disallows importing device key for: - non-unicast addresses - unicast addresses overlapping with local node address range --- doc/mesh-api.txt | 8 ++++++++ mesh/keyring.c | 9 +++++++++ mesh/manager.c | 13 +++++++++++++ 3 files changed, 30 insertions(+) diff --git a/doc/mesh-api.txt b/doc/mesh-api.txt index f2ba164a9..4fa2f9690 100644 --- a/doc/mesh-api.txt +++ b/doc/mesh-api.txt @@ -609,9 +609,13 @@ Methods: This call affects the local bluetooth-meshd key database only. + It is an error to call this with address range overlapping + with local element addresses. + PossibleErrors: org.bluez.mesh.Error.Failed org.bluez.mesh.Error.InvalidArguments + org.bluez.mesh.Error.NotAuthorized void DeleteRemoteNode(uint16 primary, uint8 count) @@ -626,8 +630,12 @@ Methods: This call affects the local bluetooth-meshd key database only. + It is an error to call this with address range overlapping + with local element addresses. + PossibleErrors: org.bluez.mesh.Error.InvalidArguments + org.bluez.mesh.Error.NotAuthorized Properties: dict Features [read-only] diff --git a/mesh/keyring.c b/mesh/keyring.c index 4c6d2986d..be17fb8a5 100644 --- a/mesh/keyring.c +++ b/mesh/keyring.c @@ -131,6 +131,9 @@ bool keyring_put_remote_dev_key(struct mesh_node *node, uint16_t unicast, if (!node) return false; + if (!IS_UNICAST(unicast) || !IS_UNICAST(unicast + count - 1)) + return false; + node_path = node_path_get(node); if (strlen(node_path) + strlen(dev_key_dir) + 1 + 4 >= PATH_MAX) @@ -221,6 +224,9 @@ bool keyring_get_remote_dev_key(struct mesh_node *node, uint16_t unicast, if (!node) return false; + if (!IS_UNICAST(unicast)) + return false; + node_path = node_path_get(node); snprintf(key_file, PATH_MAX, "%s%s/%4.4x", node_path, dev_key_dir, unicast); @@ -283,6 +289,9 @@ bool keyring_del_remote_dev_key(struct mesh_node *node, uint16_t unicast, if (!node) return false; + if (!IS_UNICAST(unicast) || !IS_UNICAST(unicast + count - 1)) + return false; + node_path = node_path_get(node); for (i = 0; i < count; i++) { snprintf(key_file, PATH_MAX, "%s%s/%4.4x", node_path, diff --git a/mesh/manager.c b/mesh/manager.c index ca3562512..d3c4b2e21 100644 --- a/mesh/manager.c +++ b/mesh/manager.c @@ -31,6 +31,7 @@ #include "mesh/node.h" #include "mesh/keyring.h" #include "mesh/manager.h" +#include "mesh/net.h" static struct l_dbus_message *add_node_call(struct l_dbus *dbus, struct l_dbus_message *msg, @@ -60,6 +61,7 @@ static struct l_dbus_message *import_node_call(struct l_dbus *dbus, void *user_data) { struct mesh_node *node = user_data; + struct mesh_net *net = node_get_net(node); struct l_dbus_message_iter iter_key; uint16_t primary; uint8_t num_ele; @@ -75,6 +77,11 @@ static struct l_dbus_message *import_node_call(struct l_dbus *dbus, return dbus_error(msg, MESH_ERROR_INVALID_ARGS, "Bad device key"); + if (mesh_net_is_local_address(net, primary) || + mesh_net_is_local_address(net, primary + num_ele - 1)) + return dbus_error(msg, MESH_ERROR_NOT_AUTHORIZED, + "Cannot overwrite local device key"); + if (!keyring_put_remote_dev_key(node, primary, num_ele, key)) return dbus_error(msg, MESH_ERROR_FAILED, NULL); @@ -86,12 +93,18 @@ static struct l_dbus_message *delete_node_call(struct l_dbus *dbus, void *user_data) { struct mesh_node *node = user_data; + struct mesh_net *net = node_get_net(node); uint16_t primary; uint8_t num_ele; if (!l_dbus_message_get_arguments(msg, "qy", &primary, &num_ele)) return dbus_error(msg, MESH_ERROR_INVALID_ARGS, NULL); + if (mesh_net_is_local_address(net, primary) || + mesh_net_is_local_address(net, primary + num_ele - 1)) + return dbus_error(msg, MESH_ERROR_NOT_AUTHORIZED, + "Cannot remove local device key"); + keyring_del_remote_dev_key(node, primary, num_ele); return l_dbus_message_new_method_return(msg); -- 2.22.0