/**
 * @file
 * @brief Shell APIs for Bluetooth BAP scan delegator
 *
 * Copyright (c) 2020-2022 Nordic Semiconductor ASA
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#include <zephyr/types.h>

#include <zephyr/kernel.h>
#include <zephyr/types.h>
#include <zephyr/shell/shell.h>
#include <stdlib.h>
#include <zephyr/bluetooth/gatt.h>
#include <zephyr/bluetooth/bluetooth.h>
#include <zephyr/bluetooth/audio/bap.h>
#include <audio/bap_internal.h>
#include "shell/bt.h"

#define PA_SYNC_INTERVAL_TO_TIMEOUT_RATIO 20 /* Set the timeout relative to interval */
#define PA_SYNC_SKIP              5

struct sync_state {
	bool pa_syncing;
	bool past_avail;
	uint8_t src_id;
	uint16_t pa_interval;
	struct k_work_delayable pa_timer;
	struct bt_conn *conn;
	struct bt_le_per_adv_sync *pa_sync;
	const struct bt_bap_scan_delegator_recv_state *recv_state;
	uint8_t broadcast_code[BT_AUDIO_BROADCAST_CODE_SIZE];
} sync_states[CONFIG_BT_BAP_SCAN_DELEGATOR_RECV_STATE_COUNT];

static bool past_preference = true;

static struct sync_state *sync_state_get(const struct bt_bap_scan_delegator_recv_state *recv_state)
{
	for (size_t i = 0U; i < ARRAY_SIZE(sync_states); i++) {
		if (sync_states[i].recv_state == recv_state) {
			return &sync_states[i];
		}
	}

	return NULL;
}

static struct sync_state *sync_state_get_or_new(
	const struct bt_bap_scan_delegator_recv_state *recv_state)
{
	struct sync_state *free_state = NULL;

	for (size_t i = 0U; i < ARRAY_SIZE(sync_states); i++) {
		if (sync_states[i].recv_state == NULL &&
		    free_state == NULL) {
			free_state = &sync_states[i];
		}

		if (sync_states[i].recv_state == recv_state) {
			return &sync_states[i];
		}
	}

	return free_state;
}

static struct sync_state *sync_state_get_by_pa(struct bt_le_per_adv_sync *sync)
{
	for (size_t i = 0U; i < ARRAY_SIZE(sync_states); i++) {
		if (sync_states[i].pa_sync == sync) {
			return &sync_states[i];
		}
	}

	return NULL;
}

static struct sync_state *sync_state_new(void)
{
	for (size_t i = 0U; i < ARRAY_SIZE(sync_states); i++) {
		if (sync_states[i].recv_state == NULL) {
			return &sync_states[i];
		}
	}

	return NULL;
}

static struct sync_state *sync_state_get_by_src_id(uint8_t src_id)
{
	for (size_t i = 0U; i < ARRAY_SIZE(sync_states); i++) {
		if (sync_states[i].src_id == src_id) {
			return &sync_states[i];
		}
	}

	return NULL;
}

static uint16_t interval_to_sync_timeout(uint16_t pa_interval)
{
	uint16_t pa_timeout;

	if (pa_interval == BT_BAP_PA_INTERVAL_UNKNOWN) {
		/* Use maximum value to maximize chance of success */
		pa_timeout = BT_GAP_PER_ADV_MAX_TIMEOUT;
	} else {
		uint32_t interval_ms;
		uint32_t timeout;

		/* Add retries and convert to unit in 10's of ms */
		interval_ms = BT_GAP_PER_ADV_INTERVAL_TO_MS(pa_interval);
		timeout = (interval_ms * PA_SYNC_INTERVAL_TO_TIMEOUT_RATIO) / 10;

		/* Enforce restraints */
		pa_timeout = CLAMP(timeout, BT_GAP_PER_ADV_MIN_TIMEOUT, BT_GAP_PER_ADV_MAX_TIMEOUT);
	}

	return pa_timeout;
}

static void pa_timer_handler(struct k_work *work)
{
	struct k_work_delayable *dwork = k_work_delayable_from_work(work);
	struct sync_state *state = CONTAINER_OF(dwork, struct sync_state, pa_timer);

	state->pa_syncing = false;

	if (state->recv_state != NULL) {
		enum bt_bap_pa_state pa_state;

		if (state->recv_state->pa_sync_state == BT_BAP_PA_STATE_INFO_REQ) {
			pa_state = BT_BAP_PA_STATE_NO_PAST;
		} else {
			pa_state = BT_BAP_PA_STATE_FAILED;
		}

		bt_bap_scan_delegator_set_pa_state(state->recv_state->src_id,
						   pa_state);

		shell_info(ctx_shell, "PA timeout for %p", state->recv_state);
	}
}

#if defined(CONFIG_BT_PER_ADV_SYNC_TRANSFER_SENDER)
static int pa_sync_past(struct bt_conn *conn,
			struct sync_state *state,
			uint16_t pa_interval)
{
	struct bt_le_per_adv_sync_transfer_param param = { 0 };
	int err;

	param.skip = PA_SYNC_SKIP;
	param.timeout = interval_to_sync_timeout(pa_interval);

	err = bt_le_per_adv_sync_transfer_subscribe(conn, &param);
	if (err != 0) {
		shell_info(ctx_shell, "Could not do PAST subscribe: %d", err);
	} else {
		shell_info(ctx_shell, "Syncing with PAST: %d", err);
		state->pa_syncing = true;
		k_work_init_delayable(&state->pa_timer, pa_timer_handler);
		(void)k_work_reschedule(&state->pa_timer,
					K_MSEC(param.timeout * 10));
	}

	return err;
}
#endif /* CONFIG_BT_PER_ADV_SYNC_TRANSFER_SENDER */

static int pa_sync_no_past(struct sync_state *state,
			    uint16_t pa_interval)
{
	const struct bt_bap_scan_delegator_recv_state *recv_state;
	struct bt_le_per_adv_sync_param param = { 0 };
	int err;

	recv_state = state->recv_state;

	bt_addr_le_copy(&param.addr, &recv_state->addr);
	param.options = BT_LE_PER_ADV_SYNC_OPT_FILTER_DUPLICATE;
	param.sid = recv_state->adv_sid;
	param.skip = PA_SYNC_SKIP;
	param.timeout = interval_to_sync_timeout(pa_interval);

	/* TODO: Validate that the advertise is broadcasting the same
	 * broadcast_id that the receive state has
	 */
	err = bt_le_per_adv_sync_create(&param, &state->pa_sync);
	if (err != 0) {
		shell_info(ctx_shell, "Could not sync per adv: %d", err);
	} else {
		char addr_str[BT_ADDR_LE_STR_LEN];

		bt_addr_le_to_str(&recv_state->addr, addr_str, sizeof(addr_str));
		shell_info(ctx_shell, "PA sync pending for addr %s", addr_str);
		state->pa_syncing = true;
		k_work_init_delayable(&state->pa_timer, pa_timer_handler);
		(void)k_work_reschedule(&state->pa_timer,
					K_MSEC(param.timeout * 10));
	}

	return err;
}

static int pa_sync_term(struct sync_state *state)
{
	int err;

	(void)k_work_cancel_delayable(&state->pa_timer);

	if (state->pa_sync == NULL) {
		return -1;
	}

	shell_info(ctx_shell, "Deleting PA sync");

	err = bt_le_per_adv_sync_delete(state->pa_sync);
	if (err != 0) {
		shell_error(ctx_shell, "Could not delete per adv sync: %d",
			    err);
	} else {
		state->pa_syncing = false;
		state->pa_sync = NULL;
	}

	return err;
}

static void recv_state_updated_cb(struct bt_conn *conn,
				  const struct bt_bap_scan_delegator_recv_state *recv_state)
{
	shell_info(ctx_shell, "Receive state with ID %u updated", recv_state->src_id);
}

static int pa_sync_req_cb(struct bt_conn *conn,
			  const struct bt_bap_scan_delegator_recv_state *recv_state,
			  bool past_avail, uint16_t pa_interval)
{
	struct sync_state *state;

	shell_info(ctx_shell,
		   "PA Sync request: past_avail %u, broadcast_id 0x%06X, pa_interval 0x%04x: %p",
		   past_avail, recv_state->broadcast_id, pa_interval,
		   recv_state);

	state = sync_state_get_or_new(recv_state);
	if (state == NULL) {
		shell_error(ctx_shell, "Could not get state");

		return -1;
	}

	state->recv_state = recv_state;
	state->src_id = recv_state->src_id;

	if (recv_state->pa_sync_state == BT_BAP_PA_STATE_SYNCED ||
	    recv_state->pa_sync_state == BT_BAP_PA_STATE_INFO_REQ) {
		/* Already syncing */
		/* TODO: Terminate existing sync and then sync to new?*/
		return -1;
	}

	if (past_avail) {
		state->past_avail = past_preference;
		state->conn = bt_conn_ref(conn);
	} else {
		state->past_avail = false;
	}

	return 0;
}

static int pa_sync_term_req_cb(struct bt_conn *conn,
			       const struct bt_bap_scan_delegator_recv_state *recv_state)
{
	struct sync_state *state;

	shell_info(ctx_shell, "PA Sync term request for %p", recv_state);

	state = sync_state_get(recv_state);
	if (state == NULL) {
		shell_error(ctx_shell, "Could not get state");

		return -1;
	}

	return pa_sync_term(state);
}

static void broadcast_code_cb(struct bt_conn *conn,
			      const struct bt_bap_scan_delegator_recv_state *recv_state,
			      const uint8_t broadcast_code[BT_AUDIO_BROADCAST_CODE_SIZE])
{
	struct sync_state *state;

	shell_info(ctx_shell, "Broadcast code received for %p", recv_state);
	shell_hexdump(ctx_shell, broadcast_code, BT_AUDIO_BROADCAST_CODE_SIZE);

	state = sync_state_get(recv_state);
	if (state == NULL) {
		shell_error(ctx_shell, "Could not get state");

		return;
	}

	(void)memcpy(state->broadcast_code, broadcast_code, BT_AUDIO_BROADCAST_CODE_SIZE);
}

static int bis_sync_req_cb(struct bt_conn *conn,
			   const struct bt_bap_scan_delegator_recv_state *recv_state,
			   const uint32_t bis_sync_req[CONFIG_BT_BAP_BASS_MAX_SUBGROUPS])
{
	printk("BIS sync request received for %p\n", recv_state);

	for (int i = 0; i < CONFIG_BT_BAP_BASS_MAX_SUBGROUPS; i++) {
		printk("  [%d]: 0x%08x\n", i, bis_sync_req[i]);
	}

	return 0;
}

static struct bt_bap_scan_delegator_cb scan_delegator_cb = {
	.recv_state_updated = recv_state_updated_cb,
	.pa_sync_req = pa_sync_req_cb,
	.pa_sync_term_req = pa_sync_term_req_cb,
	.broadcast_code = broadcast_code_cb,
	.bis_sync_req = bis_sync_req_cb,
};

static void pa_synced_cb(struct bt_le_per_adv_sync *sync,
			 struct bt_le_per_adv_sync_synced_info *info)
{
	struct sync_state *state;

	shell_info(ctx_shell, "PA %p synced", sync);

	state = sync_state_get_by_pa(sync);
	if (state == NULL) {
		shell_info(ctx_shell,
			   "Could not get sync state from PA sync %p",
			   sync);
		return;
	}

	if (state->conn != NULL) {
		bt_conn_unref(state->conn);
		state->conn = NULL;
	}

	k_work_cancel_delayable(&state->pa_timer);
}

static void pa_term_cb(struct bt_le_per_adv_sync *sync,
		       const struct bt_le_per_adv_sync_term_info *info)
{
	struct sync_state *state;

	shell_info(ctx_shell, "PA %p sync terminated", sync);

	state = sync_state_get_by_pa(sync);
	if (state == NULL) {
		shell_error(ctx_shell,
			    "Could not get sync state from PA sync %p",
			    sync);
		return;
	}

	if (state->conn != NULL) {
		bt_conn_unref(state->conn);
		state->conn = NULL;
	}

	k_work_cancel_delayable(&state->pa_timer);
}

static struct bt_le_per_adv_sync_cb pa_sync_cb =  {
	.synced = pa_synced_cb,
	.term = pa_term_cb,
};

static int cmd_bap_scan_delegator_init(const struct shell *sh, size_t argc,
				       char **argv)
{
	static bool registered;

	if (!registered) {
		bt_le_per_adv_sync_cb_register(&pa_sync_cb);
		bt_bap_scan_delegator_register_cb(&scan_delegator_cb);

		registered = true;
	}

	return 0;
}
static int cmd_bap_scan_delegator_set_past_pref(const struct shell *sh,
						size_t argc, char **argv)
{
	bool past_pref;
	int err;

	err = 0;

	past_pref = shell_strtobool(argv[1], 10, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse past_pref from %s", argv[1]);
		return -ENOEXEC;
	}

	past_preference = past_pref;

	return 0;
}

static int cmd_bap_scan_delegator_sync_pa(const struct shell *sh, size_t argc,
					  char **argv)
{
	struct sync_state *state;
	unsigned long src_id;
	int err;

	err = 0;

	src_id = shell_strtoul(argv[1], 16, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse src_id from %s", argv[1]);

		return -ENOEXEC;
	}

	if (src_id > UINT8_MAX) {
		shell_error(sh, "src_id shall be 0x00-0xff");

		return -ENOEXEC;
	}

	state = sync_state_get_by_src_id((uint8_t)src_id);
	if (state == NULL) {
		shell_error(ctx_shell, "Could not get state");

		return -ENOEXEC;
	}

	if (0) {
#if defined(CONFIG_BT_PER_ADV_SYNC_TRANSFER_SENDER)
	} else if (past_preference &&
		   state->past_avail &&
		   state->conn != NULL) {
		shell_info(sh, "Syncing with PAST");

		err = pa_sync_past(state->conn, state, state->pa_interval);
		if (err != 0) {
			err = bt_bap_scan_delegator_set_pa_state(src_id,
								 BT_BAP_PA_STATE_INFO_REQ);
			if (err != 0) {
				shell_error(sh,
					    "Failed to set INFO_REQ state: %d",
					    err);
			}

			return -ENOEXEC;
		}
#endif /* CONFIG_BT_PER_ADV_SYNC_TRANSFER_SENDER */
	} else {
		shell_info(sh, "Syncing without PAST");
		err = pa_sync_no_past(state, state->pa_interval);
	}

	if (err != 0) {
		shell_error(sh, "Failed PA sync: %d", err);

		return -ENOEXEC;
	}

	return 0;
}

static int cmd_bap_scan_delegator_term_pa(const struct shell *sh, size_t argc,
					  char **argv)
{
	struct sync_state *state;
	unsigned long src_id;
	int err;

	err = 0;

	src_id = shell_strtoul(argv[1], 16, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse src_id from %s", argv[1]);

		return -ENOEXEC;
	}

	if (src_id > UINT8_MAX) {
		shell_error(sh, "src_id shall be 0x00-0xff");

		return -ENOEXEC;
	}

	state = sync_state_get_by_src_id((uint8_t)src_id);
	if (state == NULL) {
		shell_error(ctx_shell, "Could not get state");

		return -ENOEXEC;
	}

	err = pa_sync_term(state);
	if (err != 0) {
		shell_error(ctx_shell, "Failed to terminate PA sync: %d", err);

		return -ENOEXEC;
	}

	return 0;
}

static int cmd_bap_scan_delegator_add_src(const struct shell *sh, size_t argc,
					  char **argv)
{
	/* TODO: Add support to select which PA sync to BIG sync to */
	struct bt_le_per_adv_sync *pa_sync = per_adv_syncs[0];
	struct bt_bap_bass_subgroup *subgroup_param;
	struct bt_bap_scan_delegator_add_src_param param;
	unsigned long broadcast_id;
	struct sync_state *state;
	unsigned long enc_state;
	int err;

	err = 0;

	broadcast_id = shell_strtoul(argv[1], 16, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse broadcast_id from %s", argv[1]);

		return -EINVAL;
	}

	if (broadcast_id > BT_AUDIO_BROADCAST_ID_MAX) {
		shell_error(sh, "Invalid broadcast_id %lu", broadcast_id);

		return -EINVAL;
	}

	enc_state = shell_strtoul(argv[2], 16, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse enc_state from %s", argv[2]);

		return -EINVAL;
	}

	if (enc_state > BT_BAP_BIG_ENC_STATE_BAD_CODE) {
		shell_error(sh, "Invalid enc_state %s", bt_bap_big_enc_state_str(enc_state));

		return -EINVAL;
	}

	/* TODO: Support multiple subgroups */
	subgroup_param = &param.subgroups[0];
	if (argc > 3) {
		unsigned long bis_sync;

		bis_sync = shell_strtoul(argv[3], 16, &err);
		if (err != 0) {
			shell_error(sh, "Failed to parse bis_sync from %s", argv[3]);

			return -EINVAL;
		}

		if (bis_sync > BT_BAP_BIS_SYNC_NO_PREF) {
			shell_error(sh, "Invalid bis_sync %lu", bis_sync);

			return -EINVAL;
		}
	} else {
		subgroup_param->bis_sync = 0U;
	}

	if (argc > 4) {
		subgroup_param->metadata_len = hex2bin(argv[4], strlen(argv[4]),
						       subgroup_param->metadata,
						       sizeof(subgroup_param->metadata));

		if (subgroup_param->metadata_len == 0U) {
			shell_error(sh, "Could not parse metadata");

			return -EINVAL;
		}
	} else {
		subgroup_param->metadata_len = 0U;
	}

	state = sync_state_new();
	if (state == NULL) {
		shell_error(ctx_shell, "Could not get new state");

		return -ENOEXEC;
	}

	param.pa_sync = pa_sync;
	param.encrypt_state = (enum bt_bap_big_enc_state)enc_state;
	param.broadcast_id = broadcast_id;
	param.num_subgroups = 1U;

	err = bt_bap_scan_delegator_add_src(&param);
	if (err < 0) {
		shell_error(ctx_shell, "Failed to add source: %d", err);

		return -ENOEXEC;
	}

	state->src_id = (uint8_t)err;

	return 0;
}

static int cmd_bap_scan_delegator_mod_src(const struct shell *sh, size_t argc,
					  char **argv)
{
	struct bt_bap_bass_subgroup *subgroup_param;
	struct bt_bap_scan_delegator_mod_src_param param;
	unsigned long broadcast_id;
	unsigned long enc_state;
	unsigned long src_id;
	int err;

	err = 0;

	src_id = shell_strtoul(argv[1], 16, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse src_id from %s", argv[1]);

		return -EINVAL;
	}

	if (src_id > UINT8_MAX) {
		shell_error(sh, "Invalid src_id %lu", src_id);

		return -EINVAL;
	}

	broadcast_id = shell_strtoul(argv[2], 16, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse broadcast_id from %s", argv[2]);

		return -EINVAL;
	}

	if (broadcast_id > BT_AUDIO_BROADCAST_ID_MAX) {
		shell_error(sh, "Invalid broadcast_id %lu", broadcast_id);

		return -EINVAL;
	}

	enc_state = shell_strtoul(argv[3], 16, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse enc_state from %s", argv[3]);

		return -EINVAL;
	}

	if (enc_state > BT_BAP_BIG_ENC_STATE_BAD_CODE) {
		shell_error(sh, "Invalid enc_state %s", bt_bap_big_enc_state_str(enc_state));

		return -EINVAL;
	}

	/* TODO: Support multiple subgroups */
	subgroup_param = &param.subgroups[0];
	if (argc > 4) {
		unsigned long bis_sync;

		bis_sync = shell_strtoul(argv[4], 16, &err);
		if (err != 0) {
			shell_error(sh, "Failed to parse bis_sync from %s", argv[4]);

			return -EINVAL;
		}

		if (bis_sync > BT_BAP_BIS_SYNC_NO_PREF) {
			shell_error(sh, "Invalid bis_sync %lu", bis_sync);

			return -EINVAL;
		}
	} else {
		subgroup_param->bis_sync = 0U;
	}

	if (argc > 5) {
		subgroup_param->metadata_len = hex2bin(argv[5], strlen(argv[5]),
						       subgroup_param->metadata,
						       sizeof(subgroup_param->metadata));

		if (subgroup_param->metadata_len == 0U) {
			shell_error(sh, "Could not parse metadata");

			return -EINVAL;
		}
	} else {
		subgroup_param->metadata_len = 0U;
	}


	param.src_id = (uint8_t)src_id;
	param.encrypt_state = (enum bt_bap_big_enc_state)enc_state;
	param.broadcast_id = broadcast_id;
	param.num_subgroups = 1U;

	err = bt_bap_scan_delegator_mod_src(&param);
	if (err < 0) {
		shell_error(ctx_shell, "Failed to modify source: %d", err);

		return -ENOEXEC;
	}

	return 0;
}

static int cmd_bap_scan_delegator_rem_src(const struct shell *sh, size_t argc,
					  char **argv)
{
	unsigned long src_id;
	int err;

	err = 0;

	src_id = shell_strtoul(argv[1], 16, &err);
	if (err != 0) {
		shell_error(sh, "Failed to parse src_id from %s", argv[1]);

		return -EINVAL;
	}

	if (src_id > UINT8_MAX) {
		shell_error(sh, "Invalid src_id %lu", src_id);

		return -EINVAL;
	}

	err = bt_bap_scan_delegator_rem_src((uint8_t)src_id);
	if (err < 0) {
		shell_error(ctx_shell, "Failed to remove source source: %d",
			    err);

		return -ENOEXEC;
	}

	return 0;
}

static int cmd_bap_scan_delegator_bis_synced(const struct shell *sh, size_t argc,
					 char **argv)
{
	uint32_t bis_syncs[CONFIG_BT_BAP_BASS_MAX_SUBGROUPS];
	unsigned long pa_sync_state;
	unsigned long bis_synced;
	unsigned long src_id;
	int result = 0;

	src_id = shell_strtoul(argv[1], 0, &result);
	if (result != 0) {
		shell_error(sh, "Could not parse src_id: %d", result);

		return -ENOEXEC;
	}

	if (src_id > UINT8_MAX) {
		shell_error(sh, "Invalid src_id: %lu", src_id);

		return -ENOEXEC;
	}

	pa_sync_state = shell_strtoul(argv[2], 0, &result);
	if (result != 0) {
		shell_error(sh, "Could not parse pa_sync_state: %d", result);

		return -ENOEXEC;
	}

	if (pa_sync_state > BT_BAP_PA_STATE_NO_PAST) {
		shell_error(sh, "Invalid pa_sync_state %s", bt_bap_pa_state_str(pa_sync_state));

		return -ENOEXEC;
	}

	bis_synced = shell_strtoul(argv[3], 0, &result);
	if (result != 0) {
		shell_error(sh, "Could not parse bis_synced: %d", result);

		return -ENOEXEC;
	}

	if (bis_synced > UINT32_MAX) {
		shell_error(sh, "Invalid bis_synced %ld", bis_synced);

		return -ENOEXEC;
	}

	for (size_t i = 0U; i < ARRAY_SIZE(bis_syncs); i++) {
		bis_syncs[i] = bis_synced;
	}

	result = bt_bap_scan_delegator_set_bis_sync_state(src_id, bis_syncs);
	if (result != 0) {
		shell_print(sh, "Fail: %d", result);
	}

	return result;
}

static int cmd_bap_scan_delegator(const struct shell *sh, size_t argc,
				  char **argv)
{
	if (argc > 1) {
		shell_error(sh, "%s unknown parameter: %s",
			    argv[0], argv[1]);
	} else {
		shell_error(sh, "%s Missing subcommand", argv[0]);
	}

	return -ENOEXEC;
}

SHELL_STATIC_SUBCMD_SET_CREATE(bap_scan_delegator_cmds,
	SHELL_CMD_ARG(init, NULL,
		      "Initialize the service and register callbacks",
		      cmd_bap_scan_delegator_init, 1, 0),
	SHELL_CMD_ARG(set_past_pref, NULL,
		      "Set PAST preference <true || false>",
		      cmd_bap_scan_delegator_set_past_pref, 2, 0),
	SHELL_CMD_ARG(sync_pa, NULL,
		      "Sync to PA <src_id>",
		      cmd_bap_scan_delegator_sync_pa, 2, 0),
	SHELL_CMD_ARG(term_pa, NULL,
		      "Terminate PA sync <src_id>",
		      cmd_bap_scan_delegator_term_pa, 2, 0),
	SHELL_CMD_ARG(add_src, NULL,
		      "Add a PA as source <broadcast_id> <enc_state> [bis_sync [metadata]]",
		      cmd_bap_scan_delegator_add_src, 3, 2),
	SHELL_CMD_ARG(mod_src, NULL,
		      "Modify source <src_id> <broadcast_id> <enc_state> [bis_sync [metadata]]",
		      cmd_bap_scan_delegator_mod_src, 4, 2),
	SHELL_CMD_ARG(rem_src, NULL,
		      "Remove source <src_id>",
		      cmd_bap_scan_delegator_rem_src, 2, 0),
	SHELL_CMD_ARG(synced, NULL,
		      "Set server scan state <src_id> <bis_syncs>",
		      cmd_bap_scan_delegator_bis_synced, 3, 0),
	SHELL_SUBCMD_SET_END
);

SHELL_CMD_ARG_REGISTER(bap_scan_delegator, &bap_scan_delegator_cmds,
		       "Bluetooth BAP scan delegator shell commands",
		       cmd_bap_scan_delegator, 1, 1);
