diff --git a/nimble/host/mesh/include/mesh/cfg_cli.h b/nimble/host/mesh/include/mesh/cfg_cli.h index 87ce76365..eb64fe5fc 100644 --- a/nimble/host/mesh/include/mesh/cfg_cli.h +++ b/nimble/host/mesh/include/mesh/cfg_cli.h @@ -79,13 +79,24 @@ int bt_mesh_cfg_app_key_add(u16_t net_idx, u16_t addr, u16_t key_net_idx, int bt_mesh_cfg_app_key_get(u16_t net_idx, u16_t addr, u16_t key_net_idx, u8_t *status, u16_t *keys, size_t *key_cnt); +int bt_mesh_cfg_app_key_del(uint16_t net_idx, uint16_t addr, + uint16_t key_net_idx, uint16_t key_app_idx, uint8_t *status); + int bt_mesh_cfg_mod_app_bind(u16_t net_idx, u16_t addr, u16_t elem_addr, u16_t mod_app_idx, u16_t mod_id, u8_t *status); +int bt_mesh_cfg_mod_app_unbind(uint16_t net_idx, uint16_t addr, + uint16_t elem_addr, uint16_t mod_app_idx, + uint16_t mod_id, uint8_t *status); + int bt_mesh_cfg_mod_app_bind_vnd(u16_t net_idx, u16_t addr, u16_t elem_addr, u16_t mod_app_idx, u16_t mod_id, u16_t cid, u8_t *status); +int bt_mesh_cfg_mod_app_unbind_vnd(uint16_t net_idx, uint16_t addr, + uint16_t elem_addr, uint16_t mod_app_idx, uint16_t mod_id, + uint16_t cid, uint8_t *status); + int bt_mesh_cfg_mod_app_get(u16_t net_idx, u16_t addr, u16_t elem_addr, u16_t mod_id, u8_t *status, u16_t *apps, size_t *app_cnt); diff --git a/nimble/host/mesh/src/cfg_cli.c b/nimble/host/mesh/src/cfg_cli.c index 298d88308..e60199c58 100644 --- a/nimble/host/mesh/src/cfg_cli.c +++ b/nimble/host/mesh/src/cfg_cli.c @@ -1177,6 +1177,46 @@ int bt_mesh_cfg_app_key_get(u16_t net_idx, u16_t addr, u16_t key_net_idx, return cli_wait(); } +int bt_mesh_cfg_app_key_del(uint16_t net_idx, uint16_t addr, + uint16_t key_net_idx, uint16_t key_app_idx, uint8_t *status) +{ + struct os_mbuf *msg = BT_MESH_MODEL_BUF(OP_APP_KEY_DEL, 3); + struct bt_mesh_msg_ctx ctx = { + .net_idx = net_idx, + .app_idx = BT_MESH_KEY_DEV_REMOTE, + .addr = addr, + .send_ttl = BT_MESH_TTL_DEFAULT, + }; + struct app_key_param param = { + .status = status, + .net_idx = key_net_idx, + .app_idx = key_app_idx, + }; + int err; + + err = cli_prepare(¶m, OP_APP_KEY_STATUS); + if (err) { + return err; + } + + bt_mesh_model_msg_init(msg, OP_APP_KEY_DEL); + key_idx_pack(msg, key_net_idx, key_app_idx); + + err = bt_mesh_model_send(cli->model, &ctx, msg, NULL, NULL); + if (err) { + BT_ERR("model_send() failed (err %d)", err); + cli_reset(); + return err; + } + + if (!status) { + cli_reset(); + return 0; + } + + return cli_wait(); +} + static int mod_app_bind(u16_t net_idx, u16_t addr, u16_t elem_addr, u16_t mod_app_idx, u16_t mod_id, u16_t cid, u8_t *status) @@ -1249,6 +1289,76 @@ int bt_mesh_cfg_mod_app_bind_vnd(u16_t net_idx, u16_t addr, u16_t elem_addr, status); } +static int mod_app_unbind(uint16_t net_idx, uint16_t addr, uint16_t elem_addr, + uint16_t mod_app_idx, uint16_t mod_id, uint16_t cid, + uint8_t *status) +{ + struct os_mbuf *msg = BT_MESH_MODEL_BUF(OP_MOD_APP_UNBIND, 8); + struct bt_mesh_msg_ctx ctx = { + .net_idx = net_idx, + .app_idx = BT_MESH_KEY_DEV_REMOTE, + .addr = addr, + .send_ttl = BT_MESH_TTL_DEFAULT, + }; + struct mod_app_param param = { + .status = status, + .elem_addr = elem_addr, + .mod_app_idx = mod_app_idx, + .mod_id = mod_id, + .cid = cid, + }; + int err; + + err = cli_prepare(¶m, OP_MOD_APP_STATUS); + if (err) { + return err; + } + + bt_mesh_model_msg_init(msg, OP_MOD_APP_UNBIND); + net_buf_simple_add_le16(msg, elem_addr); + net_buf_simple_add_le16(msg, mod_app_idx); + + if (cid != CID_NVAL) { + net_buf_simple_add_le16(msg, cid); + } + + net_buf_simple_add_le16(msg, mod_id); + + err = bt_mesh_model_send(cli->model, &ctx, msg, NULL, NULL); + if (err) { + BT_ERR("model_send() failed (err %d)", err); + cli_reset(); + return err; + } + + if (!status) { + cli_reset(); + return 0; + } + + return cli_wait(); +} + +int bt_mesh_cfg_mod_app_unbind(uint16_t net_idx, uint16_t addr, + uint16_t elem_addr, uint16_t mod_app_idx, + uint16_t mod_id, uint8_t *status) +{ + return mod_app_unbind(net_idx, addr, elem_addr, mod_app_idx, mod_id, + CID_NVAL, status); +} + +int bt_mesh_cfg_mod_app_unbind_vnd(uint16_t net_idx, uint16_t addr, + uint16_t elem_addr, uint16_t mod_app_idx, + uint16_t mod_id, uint16_t cid, uint8_t *status) +{ + if (cid == CID_NVAL) { + return -EINVAL; + } + + return mod_app_unbind(net_idx, addr, elem_addr, mod_app_idx, + mod_id, cid, status); +} + static int mod_member_list_get(u32_t op, u32_t expect_op, u16_t net_idx, u16_t addr, u16_t elem_addr, u16_t mod_id, u16_t cid, u8_t *status, u16_t *apps, diff --git a/nimble/host/mesh/src/shell.c b/nimble/host/mesh/src/shell.c index 7b35291fc..6ea500172 100644 --- a/nimble/host/mesh/src/shell.c +++ b/nimble/host/mesh/src/shell.c @@ -1360,7 +1360,7 @@ struct shell_cmd_help cmd_net_key_get_help = { NULL, NULL, NULL }; -static int cmd_net_key_del(size_t argc, char *argv[]) +static int cmd_net_key_del(int argc, char *argv[]) { uint16_t key_net_idx; uint8_t status; @@ -1496,6 +1496,41 @@ struct shell_cmd_help cmd_app_key_get_help = { NULL, "", NULL }; +static int cmd_app_key_del(int argc, char *argv[]) +{ + uint16_t key_net_idx, key_app_idx; + uint8_t status; + int err; + + if (argc < 3) { + return -EINVAL; + } + + key_net_idx = strtoul(argv[1], NULL, 0); + key_app_idx = strtoul(argv[2], NULL, 0); + + err = bt_mesh_cfg_app_key_del(net.net_idx, net.dst, key_net_idx, + key_app_idx, &status); + if (err) { + printk("Unable to send App Key del(err %d)", err); + return 0; + } + + if (status) { + printk("AppKeyDel failed with status 0x%02x", + status); + } else { + printk("AppKey deleted, NetKeyIndex 0x%04x " + "AppKeyIndex 0x%04x", key_net_idx, key_app_idx); + } + + return 0; +} + +struct shell_cmd_help cmd_app_key_del_help = { + NULL, " ", NULL +}; + static int cmd_mod_app_bind(int argc, char *argv[]) { u16_t elem_addr, mod_app_idx, mod_id, cid; @@ -1538,6 +1573,50 @@ struct shell_cmd_help cmd_mod_app_bind_help = { NULL, " [Company ID]", NULL }; +static int cmd_mod_app_unbind(int argc, char *argv[]) +{ + uint16_t elem_addr, mod_app_idx, mod_id, cid; + uint8_t status; + int err; + + if (argc < 4) { + return -EINVAL; + } + + elem_addr = strtoul(argv[1], NULL, 0); + mod_app_idx = strtoul(argv[2], NULL, 0); + mod_id = strtoul(argv[3], NULL, 0); + + if (argc > 4) { + cid = strtoul(argv[4], NULL, 0); + err = bt_mesh_cfg_mod_app_unbind_vnd(net.net_idx, net.dst, + elem_addr, mod_app_idx, + mod_id, cid, &status); + } else { + err = bt_mesh_cfg_mod_app_unbind(net.net_idx, net.dst, + elem_addr, mod_app_idx, mod_id, &status); + } + + if (err) { + printk("Unable to send Model App Unbind (err %d)", + err); + return 0; + } + + if (status) { + printk("Model App Unbind failed with status 0x%02x", + status); + } else { + printk("AppKey successfully unbound"); + } + + return 0; +} + +struct shell_cmd_help cmd_mod_app_unbind_help = { + NULL, " [Company ID]", NULL +}; + static int cmd_mod_app_get(int argc, char *argv[]) { @@ -3308,13 +3387,18 @@ static const struct shell_cmd mesh_commands[] = { { .sc_cmd = "net-key-del", .sc_cmd_func = cmd_net_key_del, - .help = &cmdcmd_net_key_del_help, + .help = &cmd_net_key_del_help, }, { .sc_cmd = "app-key-add", .sc_cmd_func = cmd_app_key_add, .help = &cmd_app_key_add_help, }, + { + .sc_cmd = "app-key-del", + .sc_cmd_func = cmd_app_key_del, + .help = &cmd_app_key_del_help, + }, { .sc_cmd = "app-key-get", .sc_cmd_func = cmd_app_key_get, @@ -3330,6 +3414,11 @@ static const struct shell_cmd mesh_commands[] = { .sc_cmd_func = cmd_mod_app_get, .help = &cmd_mod_app_get_help, }, + { + .sc_cmd = "mod-app-unbind", + .sc_cmd_func = cmd_mod_app_unbind, + .help = &cmd_mod_app_unbind_help, + }, { .sc_cmd = "mod-pub", .sc_cmd_func = cmd_mod_pub,