/*  Bluetooth ISO */

/*
 * Copyright (c) 2020 Intel Corporation
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#include <zephyr.h>
#include <sys/byteorder.h>
#include <sys/check.h>

#include <bluetooth/hci.h>
#include <bluetooth/bluetooth.h>
#include <bluetooth/conn.h>
#include <bluetooth/iso.h>

#include "host/hci_core.h"
#include "host/conn_internal.h"
#include "iso_internal.h"

#define BT_DBG_ENABLED IS_ENABLED(CONFIG_BT_DEBUG_ISO)
#define LOG_MODULE_NAME bt_iso
#include "common/log.h"

NET_BUF_POOL_FIXED_DEFINE(iso_tx_pool, CONFIG_BT_ISO_TX_BUF_COUNT,
			  CONFIG_BT_ISO_TX_MTU, NULL);
NET_BUF_POOL_FIXED_DEFINE(iso_rx_pool, CONFIG_BT_ISO_RX_BUF_COUNT,
			  CONFIG_BT_ISO_RX_MTU, NULL);

static struct bt_iso_recv_info iso_info_data[CONFIG_BT_ISO_RX_BUF_COUNT];
#define iso_info(buf) (&iso_info_data[net_buf_id(buf)])

#if CONFIG_BT_ISO_TX_FRAG_COUNT > 0
NET_BUF_POOL_FIXED_DEFINE(iso_frag_pool, CONFIG_BT_ISO_TX_FRAG_COUNT,
			  CONFIG_BT_ISO_TX_MTU, NULL);
#endif /* CONFIG_BT_ISO_TX_FRAG_COUNT > 0 */

/* TODO: Allow more than one server? */
static struct bt_iso_server *iso_server;
struct bt_conn iso_conns[CONFIG_BT_ISO_MAX_CHAN];
#if defined(CONFIG_BT_ISO_BROADCAST)
struct bt_iso_big bigs[CONFIG_BT_ISO_MAX_BIG];
#endif /* defined(CONFIG_BT_ISO_BROADCAST) */


struct bt_iso_data_path {
	/* Data Path direction */
	uint8_t dir;
	/* Data Path ID */
	uint8_t pid;
	/* Data Path param reference */
	struct bt_iso_chan_path *path;
};


struct net_buf *bt_iso_get_rx(k_timeout_t timeout)
{
	struct net_buf *buf = net_buf_alloc(&iso_rx_pool, timeout);

	if (buf) {
		net_buf_reserve(buf, BT_BUF_RESERVE);
		bt_buf_set_type(buf, BT_BUF_ISO_IN);
	}

	return buf;
}

void hci_iso(struct net_buf *buf)
{
	struct bt_hci_iso_hdr *hdr;
	uint16_t handle, len;
	struct bt_conn *conn;
	uint8_t flags;

	BT_DBG("buf %p", buf);

	BT_ASSERT(buf->len >= sizeof(*hdr));

	hdr = net_buf_pull_mem(buf, sizeof(*hdr));
	len = sys_le16_to_cpu(hdr->len);
	handle = sys_le16_to_cpu(hdr->handle);
	flags = bt_iso_flags(handle);

	iso(buf)->handle = bt_iso_handle(handle);
	iso(buf)->index = BT_CONN_INDEX_INVALID;

	BT_DBG("handle %u len %u flags %u", iso(buf)->handle, len, flags);

	if (buf->len != len) {
		BT_ERR("ISO data length mismatch (%u != %u)", buf->len, len);
		net_buf_unref(buf);
		return;
	}

	conn = bt_conn_lookup_handle(iso(buf)->handle);
	if (!conn) {
		BT_ERR("Unable to find conn for handle %u", iso(buf)->handle);
		net_buf_unref(buf);
		return;
	}

	iso(buf)->index = bt_conn_index(conn);

	bt_conn_recv(conn, buf, flags);
	bt_conn_unref(conn);
}

void hci_le_cis_estabilished(struct net_buf *buf)
{
	struct bt_hci_evt_le_cis_established *evt = (void *)buf->data;
	uint16_t handle = sys_le16_to_cpu(evt->conn_handle);
	struct bt_conn *conn;

	BT_DBG("status %u handle %u", evt->status, handle);

	/* ISO connection handles are already assigned at this point */
	conn = bt_conn_lookup_handle(handle);
	if (!conn) {
		BT_ERR("No connection found for handle %u", handle);
		return;
	}

	CHECKIF(conn->type != BT_CONN_TYPE_ISO) {
		BT_DBG("Invalid connection type %u", conn->type);
		return;
	}

	if (!evt->status) {
		/* TODO: Add CIG sync delay */
		bt_conn_set_state(conn, BT_CONN_CONNECTED);
		bt_conn_unref(conn);
		return;
	}

	conn->err = evt->status;
	bt_iso_disconnected(conn);
	bt_conn_unref(conn);
}

int hci_le_reject_cis(uint16_t handle, uint8_t reason)
{
	struct bt_hci_cp_le_reject_cis *cp;
	struct net_buf *buf;
	int err;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_REJECT_CIS, sizeof(*cp));
	if (!buf) {
		return -ENOBUFS;
	}

	cp = net_buf_add(buf, sizeof(*cp));
	cp->handle = sys_cpu_to_le16(handle);
	cp->reason = reason;

	err = bt_hci_cmd_send_sync(BT_HCI_OP_LE_REJECT_CIS, buf, NULL);
	if (err) {
		return err;
	}

	return 0;
}

int hci_le_accept_cis(uint16_t handle)
{
	struct bt_hci_cp_le_accept_cis *cp;
	struct net_buf *buf;
	int err;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_ACCEPT_CIS, sizeof(*cp));
	if (!buf) {
		return -ENOBUFS;
	}

	cp = net_buf_add(buf, sizeof(*cp));
	cp->handle = sys_cpu_to_le16(handle);

	err = bt_hci_cmd_send_sync(BT_HCI_OP_LE_ACCEPT_CIS, buf, NULL);
	if (err) {
		return err;
	}

	return 0;
}

void hci_le_cis_req(struct net_buf *buf)
{
	struct bt_hci_evt_le_cis_req *evt = (void *)buf->data;
	uint16_t acl_handle = sys_le16_to_cpu(evt->acl_handle);
	uint16_t cis_handle = sys_le16_to_cpu(evt->cis_handle);
	struct bt_conn *conn, *iso;
	int err;

	BT_DBG("acl_handle %u cis_handle %u cig_id %u cis %u",
		acl_handle, cis_handle, evt->cig_id, evt->cis_id);

	/* Lookup existing connection with same handle */
	iso = bt_conn_lookup_handle(cis_handle);
	if (iso) {
		BT_ERR("Invalid ISO handle %u", cis_handle);
		hci_le_reject_cis(cis_handle, BT_HCI_ERR_CONN_LIMIT_EXCEEDED);
		bt_conn_unref(iso);
		return;
	}

	/* Lookup ACL connection to attach */
	conn = bt_conn_lookup_handle(acl_handle);
	if (!conn) {
		BT_ERR("Invalid ACL handle %u", acl_handle);
		hci_le_reject_cis(cis_handle, BT_HCI_ERR_UNKNOWN_CONN_ID);
		return;
	}

	/* Add ISO connection */
	iso = bt_conn_add_iso(conn);

	bt_conn_unref(conn);

	if (!iso) {
		BT_ERR("Could not create and add ISO to conn %u", acl_handle);
		hci_le_reject_cis(cis_handle,
				  BT_HCI_ERR_INSUFFICIENT_RESOURCES);
		return;
	}

	iso->iso.cig_id = evt->cig_id;
	iso->iso.cis_id = evt->cis_id;

	/* Request application to accept */
	err = bt_iso_accept(iso);
	if (err) {
		BT_DBG("App rejected ISO %d", err);
		bt_conn_unref(iso);
		hci_le_reject_cis(cis_handle,
				  BT_HCI_ERR_INSUFFICIENT_RESOURCES);
		return;
	}

	iso->handle = cis_handle;
	iso->role = BT_HCI_ROLE_SLAVE;
	bt_conn_set_state(iso, BT_CONN_CONNECT);

	err = hci_le_accept_cis(cis_handle);
	if (err) {
		bt_conn_unref(iso);
		hci_le_reject_cis(cis_handle,
				  BT_HCI_ERR_INSUFFICIENT_RESOURCES);
		return;
	}
}

int hci_le_remove_cig(uint8_t cig_id)
{
	struct bt_hci_cp_le_remove_cig *req;
	struct net_buf *buf;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_REMOVE_CIG, sizeof(*req));
	if (!buf) {
		return -ENOBUFS;
	}

	req = net_buf_add(buf, sizeof(*req));

	memset(req, 0, sizeof(*req));

	req->cig_id = cig_id;

	return bt_hci_cmd_send_sync(BT_HCI_OP_LE_REMOVE_CIG, buf, NULL);
}

void bt_iso_cleanup(struct bt_conn *conn)
{
	struct bt_conn_iso *iso = bt_conn_iso(conn);
	int i;

	BT_DBG("%p", conn);

	/* Check if ISO connection is in fact a BIS */
	if (!iso->acl) {
		return;
	}

	bt_conn_unref(iso->acl);
	iso->acl = NULL;

	/* Check if conn is last of CIG */
	for (i = 0; i < CONFIG_BT_ISO_MAX_CHAN; i++) {
		if (conn == &iso_conns[i]) {
			continue;
		}

		if (atomic_get(&iso_conns[i].ref) &&
		    iso_conns[i].iso.cig_id == conn->iso.cig_id) {
			break;
		}
	}

	if (i == CONFIG_BT_ISO_MAX_CHAN) {
		hci_le_remove_cig(conn->iso.cig_id);
	}
}

struct bt_conn *iso_new(void)
{
	struct bt_conn *iso = bt_conn_new(iso_conns, ARRAY_SIZE(iso_conns));

	if (iso) {
		iso->type = BT_CONN_TYPE_ISO;
		sys_slist_init(&iso->channels);
	} else {
		BT_DBG("Could not create new ISO");
	}
	return iso;
}

struct bt_conn *bt_conn_add_iso(struct bt_conn *acl)
{
	struct bt_conn *conn = iso_new();

	if (!conn) {
		BT_ERR("Unable to allocate connection");
		return NULL;
	}

	conn->iso.acl = bt_conn_ref(acl);

	return conn;
}

#if defined(CONFIG_NET_BUF_LOG)
struct net_buf *bt_iso_create_pdu_timeout_debug(struct net_buf_pool *pool,
						size_t reserve,
						k_timeout_t timeout,
						const char *func, int line)
#else
struct net_buf *bt_iso_create_pdu_timeout(struct net_buf_pool *pool,
					  size_t reserve, k_timeout_t timeout)
#endif
{
	if (!pool) {
		pool = &iso_tx_pool;
	}

	reserve += sizeof(struct bt_hci_iso_data_hdr);

#if defined(CONFIG_NET_BUF_LOG)
	return bt_conn_create_pdu_timeout_debug(pool, reserve, timeout, func,
						line);
#else
	return bt_conn_create_pdu_timeout(pool, reserve, timeout);
#endif
}

#if defined(CONFIG_NET_BUF_LOG)
struct net_buf *bt_iso_create_frag_timeout_debug(size_t reserve,
						 k_timeout_t timeout,
						 const char *func, int line)
#else
struct net_buf *bt_iso_create_frag_timeout(size_t reserve, k_timeout_t timeout)
#endif
{
	struct net_buf_pool *pool = NULL;

#if CONFIG_BT_ISO_TX_FRAG_COUNT > 0
	pool = &iso_frag_pool;
#endif /* CONFIG_BT_ISO_TX_FRAG_COUNT > 0 */

#if defined(CONFIG_NET_BUF_LOG)
	return bt_conn_create_pdu_timeout_debug(pool, reserve, timeout, func,
						line);
#else
	return bt_conn_create_pdu_timeout(pool, reserve, timeout);
#endif
}

static struct net_buf *hci_le_set_cig_params(struct bt_iso_create_param *param)
{
	struct bt_hci_cis_params *cis;
	struct bt_hci_cp_le_set_cig_params *req;
	struct net_buf *buf;
	struct net_buf *rsp;
	int i, err;

	if (!param->chans[0]->qos->tx && !param->chans[0]->qos->rx) {
		BT_ERR("Both TX and RX QoS are disabled");
		return NULL;
	}

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_SET_CIG_PARAMS,
				sizeof(*req) + sizeof(*cis) * param->num_conns);
	if (!buf) {
		return NULL;
	}

	req = net_buf_add(buf, sizeof(*req));

	memset(req, 0, sizeof(*req));

	req->cig_id = param->conns[0]->iso.cig_id;
	if (param->chans[0]->qos->tx) {
		sys_put_le24(param->chans[0]->qos->tx->interval, req->m_interval);
		req->m_latency = sys_cpu_to_le16(param->chans[0]->qos->tx->latency);
	} else {
		/* Use RX values if TX is disabled.
		 * If TX is disabled then the values don't have any meaning, as
		 * we will create a new CIG in case we want to change the
		 * directions, but will need to be set to the fields to some
		 * valid (nonzero) values for the controller to accept them.
		 */
		sys_put_le24(param->chans[0]->qos->rx->interval, req->m_interval);
		req->m_latency = sys_cpu_to_le16(param->chans[0]->qos->rx->latency);
	}

	if (param->chans[0]->qos->rx) {
		sys_put_le24(param->chans[0]->qos->rx->interval, req->s_interval);
		req->s_latency = sys_cpu_to_le16(param->chans[0]->qos->rx->latency);
	} else {
		/* Use TX values if RX is disabled.
		 * If RX is disabled then the values don't have any meaning, as
		 * we will create a new CIG in case we want to change the
		 * directions, but will need to be set to the fields to some
		 * valid (nonzero) values for the controller to accept them.
		 */
		sys_put_le24(param->chans[0]->qos->tx->interval, req->s_interval);
		req->s_latency = sys_cpu_to_le16(param->chans[0]->qos->tx->latency);
	}

	req->sca = param->chans[0]->qos->sca;
	req->packing = param->chans[0]->qos->packing;
	req->framing = param->chans[0]->qos->framing;
	req->num_cis = param->num_conns;

	/* Program the cis parameters */
	for (i = 0; i < param->num_conns; i++) {
		struct bt_iso_chan_qos *qos = param->chans[i]->qos;

		cis = net_buf_add(buf, sizeof(*cis));

		memset(cis, 0, sizeof(*cis));

		cis->cis_id = param->conns[i]->iso.cis_id;

		if (!qos->tx && !qos->rx) {
			BT_ERR("Both TX and RX QoS are disabled");
			net_buf_unref(buf);
			return NULL;
		}

		if (!qos->tx) {
			/* Use RX PHY if TX is not set (disabled) */
			cis->m_phy = qos->rx->phy;
		} else {
			cis->m_sdu = sys_cpu_to_le16(qos->tx->sdu);
			cis->m_phy = qos->tx->phy;
			cis->m_rtn = qos->tx->rtn;
		}

		if (!qos->rx) {
			/* Use TX PHY if RX is not set (disabled) */
			cis->s_phy = qos->tx->phy;
		} else {
			cis->s_sdu = sys_cpu_to_le16(qos->rx->sdu);
			cis->s_phy = qos->rx->phy;
			cis->s_rtn = qos->rx->rtn;
		}
	}

	err = bt_hci_cmd_send_sync(BT_HCI_OP_LE_SET_CIG_PARAMS, buf, &rsp);
	if (err) {
		return NULL;
	}

	return rsp;
}

int bt_conn_bind_iso(struct bt_iso_create_param *param)
{
	struct bt_conn *conn;
	struct net_buf *rsp;
	struct bt_hci_rp_le_set_cig_params *cig_rsp;
	int i, err;

	/* Check if controller is ISO capable */
	if (!BT_FEAT_LE_CIS_MASTER(bt_dev.le.features)) {
		return -ENOTSUP;
	}

	if (!param->num_conns || param->num_conns > CONFIG_BT_ISO_MAX_CHAN) {
		return -EINVAL;
	}

	/* Assign ISO connections to each LE connection */
	for (i = 0; i < param->num_conns; i++) {
		conn = param->conns[i];

		if (conn->type != BT_CONN_TYPE_LE) {
			err = -EINVAL;
			goto failed;
		}

		conn = bt_conn_add_iso(conn);
		if (!conn) {
			err = -ENOMEM;
			goto failed;
		}

		conn->iso.cig_id = param->id;
		conn->iso.cis_id = bt_conn_index(conn);

		param->conns[i] = conn;
	}

	rsp = hci_le_set_cig_params(param);
	if (!rsp) {
		err = -EIO;
		goto failed;
	}

	cig_rsp = (void *)rsp->data;

	if (rsp->len < sizeof(cig_rsp) ||
	    cig_rsp->num_handles != param->num_conns) {
		BT_WARN("Unexpected response to hci_le_set_cig_params");
		err = -EIO;
		net_buf_unref(rsp);
		goto failed;
	}

	for (i = 0; i < cig_rsp->num_handles; i++) {
		/* Assign the connection handle */
		param->conns[i]->handle = cig_rsp->handle[i];
	}

	net_buf_unref(rsp);

	return 0;

failed:
	for (i = 0; i < param->num_conns; i++) {
		conn = param->conns[i];

		if (conn->type == BT_CONN_TYPE_ISO) {
			bt_iso_cleanup(conn);
		}
	}

	return err;
}

static int hci_le_create_cis(struct bt_conn **conn, uint8_t num_conns)
{
	struct bt_hci_cis *cis;
	struct bt_hci_cp_le_create_cis *req;
	struct net_buf *buf;
	int i;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_CREATE_CIS,
				sizeof(*req) + sizeof(*cis) * num_conns);
	if (!buf) {
		return -ENOBUFS;
	}

	req = net_buf_add(buf, sizeof(*req));

	memset(req, 0, sizeof(*req));

	req->num_cis = num_conns;

	/* Program the cis parameters */
	for (i = 0; i < num_conns; i++) {
		cis = net_buf_add(buf, sizeof(*cis));

		memset(cis, 0, sizeof(*cis));

		cis->cis_handle = sys_cpu_to_le16(conn[i]->handle);
		cis->acl_handle = sys_cpu_to_le16(conn[i]->iso.acl->handle);
	}

	return bt_hci_cmd_send_sync(BT_HCI_OP_LE_CREATE_CIS, buf, NULL);
}

int bt_conn_connect_iso(struct bt_conn **conns, uint8_t num_conns)
{
	int i, err;

	/* Check if controller is ISO capable */
	if (!BT_FEAT_LE_CIS_MASTER(bt_dev.le.features)) {
		return -ENOTSUP;
	}

	if (num_conns > CONFIG_BT_ISO_MAX_CHAN) {
		return -EINVAL;
	}

	for (i = 0; i < num_conns; i++) {
		if (conns[i]->type != BT_CONN_TYPE_ISO) {
			return -EINVAL;
		}
	}

	err = hci_le_create_cis(conns, num_conns);
	if (err) {
		return err;
	}

	/* Set connection state */
	for (i = 0; i < num_conns; i++) {
		bt_conn_set_state(conns[i], BT_CONN_CONNECT);
	}

	return 0;
}

static int hci_le_setup_iso_data_path(struct bt_conn *conn,
				      struct bt_iso_data_path *path)
{
	struct bt_hci_cp_le_setup_iso_path *cp;
	struct bt_hci_rp_le_setup_iso_path *rp;
	struct net_buf *buf, *rsp;
	uint8_t *cc;
	int err;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_SETUP_ISO_PATH, sizeof(*cp));
	if (!buf) {
		return -ENOBUFS;
	}

	cp = net_buf_add(buf, sizeof(*cp));
	cp->handle = sys_cpu_to_le16(conn->handle);
	cp->path_dir = path->dir;
	cp->path_id = path->pid;
	cp->codec_id.coding_format = path->path->format;
	cp->codec_id.company_id = sys_cpu_to_le16(path->path->cid);
	cp->codec_id.vs_codec_id = sys_cpu_to_le16(path->path->vid);
	sys_put_le24(path->path->delay, cp->controller_delay);
	cp->codec_config_len = path->path->cc_len;
	cc = net_buf_add(buf, cp->codec_config_len);
	memcpy(cc, path->path->cc, cp->codec_config_len);

	err = bt_hci_cmd_send_sync(BT_HCI_OP_LE_SETUP_ISO_PATH, buf, &rsp);
	if (err) {
		return err;
	}

	rp = (void *)rsp->data;
	if (rp->status || (sys_le16_to_cpu(rp->handle) != conn->handle)) {
		err = -EIO;
	}

	net_buf_unref(rsp);

	return err;
}

static int hci_le_remove_iso_data_path(struct bt_conn *conn, uint8_t dir)
{
	struct bt_hci_cp_le_remove_iso_path *cp;
	struct bt_hci_rp_le_remove_iso_path *rp;
	struct net_buf *buf, *rsp;
	int err;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_REMOVE_ISO_PATH, sizeof(*cp));
	if (!buf) {
		return -ENOBUFS;
	}

	cp = net_buf_add(buf, sizeof(*cp));
	cp->handle = conn->handle;
	cp->path_dir = dir;

	err = bt_hci_cmd_send_sync(BT_HCI_OP_LE_REMOVE_ISO_PATH, buf, &rsp);
	if (err) {
		return err;
	}

	rp = (void *)rsp->data;
	if (rp->status || (sys_le16_to_cpu(rp->handle) != conn->handle)) {
		err = -EIO;
	}

	net_buf_unref(rsp);

	return err;
}

static void bt_iso_chan_add(struct bt_conn *conn, struct bt_iso_chan *chan)
{
	/* Attach channel to the connection */
	sys_slist_append(&conn->channels, &chan->node);
	chan->conn = conn;

	BT_DBG("conn %p chan %p", conn, chan);
}

int bt_iso_accept(struct bt_conn *conn)
{
	struct bt_iso_chan *chan;
	int err;

	CHECKIF(!conn || conn->type != BT_CONN_TYPE_ISO) {
		BT_DBG("Invalid parameters: conn %p conn->type %u", conn,
		       conn ? conn->type : 0);
		return -EINVAL;
	}

	BT_DBG("%p", conn);

	if (!iso_server) {
		return -ENOMEM;
	}

	err = iso_server->accept(conn, &chan);
	if (err < 0) {
		BT_ERR("err %d", err);
		return err;
	}

	bt_iso_chan_add(conn, chan);
	bt_iso_chan_set_state(chan, BT_ISO_BOUND);

	return 0;
}

static int bt_iso_setup_data_path(struct bt_conn *conn)
{
	int err;
	struct bt_iso_chan *chan;
	struct bt_iso_chan_path default_path = { .pid = BT_ISO_DATA_PATH_HCI };
	struct bt_iso_data_path out_path = {
		.dir = BT_HCI_DATAPATH_DIR_CTLR_TO_HOST };
	struct bt_iso_data_path in_path = {
		.dir = BT_HCI_DATAPATH_DIR_HOST_TO_CTLR };
	struct bt_iso_chan_io_qos *tx_qos;
	struct bt_iso_chan_io_qos *rx_qos;

	chan = SYS_SLIST_PEEK_HEAD_CONTAINER(&conn->channels, chan, node);
	if (!chan) {
		return -EINVAL;
	}

	tx_qos = chan->qos->tx;
	rx_qos = chan->qos->rx;

	in_path.path = tx_qos && tx_qos->path ? tx_qos->path : &default_path;
	out_path.path = rx_qos && rx_qos->path ? rx_qos->path : &default_path;

	if (!tx_qos) {
		in_path.pid = BT_ISO_DATA_PATH_DISABLED;
	}

	if (!rx_qos) {
		out_path.pid = BT_ISO_DATA_PATH_DISABLED;
	}

	if (conn->iso.is_bis) {
		/* Only set one data path for BIS as per the spec */
		if (tx_qos) {
			return hci_le_setup_iso_data_path(conn, &in_path);

		} else {
			return hci_le_setup_iso_data_path(conn, &out_path);
		}

	} else {
		/* Setup both directions for CIS*/
		err = hci_le_setup_iso_data_path(conn, &in_path);
		if (err) {
			return err;
		}

		return hci_le_setup_iso_data_path(conn, &out_path);

	}
}

void bt_iso_connected(struct bt_conn *conn)
{
	struct bt_iso_chan *chan;

	CHECKIF(!conn || conn->type != BT_CONN_TYPE_ISO) {
		BT_DBG("Invalid parameters: conn %p conn->type %u", conn,
		       conn ? conn->type : 0);
		return;
	}

	BT_DBG("%p", conn);

	if (bt_iso_setup_data_path(conn)) {
		BT_ERR("Unable to setup data path");
		bt_conn_disconnect(conn, BT_HCI_ERR_REMOTE_USER_TERM_CONN);
		return;
	}

	SYS_SLIST_FOR_EACH_CONTAINER(&conn->channels, chan, node) {
		bt_iso_chan_set_state(chan, BT_ISO_CONNECTED);

		if (chan->ops->connected) {
			chan->ops->connected(chan);
		}
	}
}

static void bt_iso_remove_data_path(struct bt_conn *conn)
{
	BT_DBG("%p", conn);

	if (conn->iso.is_bis) {
		struct bt_iso_chan *chan;
		struct bt_iso_chan_io_qos *tx_qos;
		uint8_t dir;

		chan = SYS_SLIST_PEEK_HEAD_CONTAINER(&conn->channels, chan, node);
		if (!chan) {
			return;
		}

		tx_qos = chan->qos->tx;

		/* Only remove one data path for BIS as per the spec */
		if (tx_qos) {
			dir = BT_HCI_DATAPATH_DIR_HOST_TO_CTLR;
		} else {
			dir = BT_HCI_DATAPATH_DIR_CTLR_TO_HOST;
		}

		(void)hci_le_remove_iso_data_path(conn, dir);
	} else {
		/* Remove both directions for CIS*/

		/* TODO: Check which has been setup first to avoid removing
		 * data paths that are not setup
		 */
		(void)hci_le_remove_iso_data_path(conn,
						  BT_HCI_DATAPATH_DIR_CTLR_TO_HOST);
		(void)hci_le_remove_iso_data_path(conn,
						  BT_HCI_DATAPATH_DIR_HOST_TO_CTLR);
	}
}

static void bt_iso_chan_disconnected(struct bt_iso_chan *chan, uint8_t reason)
{
	BT_DBG("%p, reason 0x%02x", chan, reason);

	if (!chan->conn) {
		bt_iso_chan_set_state(chan, BT_ISO_DISCONNECTED);
		return;
	}

	if (chan->conn->iso.is_bis) {
		bt_iso_chan_set_state(chan, BT_ISO_DISCONNECTED);
	} else {
		bt_iso_chan_set_state(chan, BT_ISO_BOUND);

		/* Unbind if acting as slave or ACL has been disconnected */
		if (chan->conn->role == BT_HCI_ROLE_SLAVE ||
		    chan->conn->iso.acl->state == BT_CONN_DISCONNECTED) {
			bt_iso_chan_unbind(chan);
		}
	}

	if (chan->ops->disconnected) {
		chan->ops->disconnected(chan, reason);
	}
}

void bt_iso_disconnected(struct bt_conn *conn)
{
	struct bt_iso_chan *chan, *next;

	CHECKIF(!conn || conn->type != BT_CONN_TYPE_ISO) {
		BT_DBG("Invalid parameters: conn %p conn->type %u", conn,
		       conn ? conn->type : 0);
		return;
	}

	BT_DBG("%p", conn);

	if (sys_slist_is_empty(&conn->channels)) {
		return;
	}

	bt_iso_remove_data_path(conn);

	SYS_SLIST_FOR_EACH_CONTAINER_SAFE(&conn->channels, chan, next, node) {
		bt_iso_chan_disconnected(chan, conn->err);
	}
}

int bt_iso_server_register(struct bt_iso_server *server)
{
	CHECKIF(!server) {
		BT_DBG("Invalid parameter: server %p", server);
		return -EINVAL;
	}

	/* Check if controller is ISO capable */
	if (!BT_FEAT_LE_CIS_SLAVE(bt_dev.le.features)) {
		return -ENOTSUP;
	}

	if (iso_server) {
		return -EADDRINUSE;
	}

	if (!server->accept) {
		return -EINVAL;
	}

	if (server->sec_level > BT_SECURITY_L3) {
		return -EINVAL;
	} else if (server->sec_level < BT_SECURITY_L1) {
		/* Level 0 is only applicable for BR/EDR */
		server->sec_level = BT_SECURITY_L1;
	}

	BT_DBG("%p", server);

	iso_server = server;

	return 0;
}

#if defined(CONFIG_BT_DEBUG_ISO)
const char *bt_iso_chan_state_str(uint8_t state)
{
	switch (state) {
	case BT_ISO_DISCONNECTED:
		return "disconnected";
	case BT_ISO_BOUND:
		return "bound";
	case BT_ISO_CONNECT:
		return "connect";
	case BT_ISO_CONNECTED:
		return "connected";
	case BT_ISO_DISCONNECT:
		return "disconnect";
	default:
		return "unknown";
	}
}

void bt_iso_chan_set_state_debug(struct bt_iso_chan *chan, uint8_t state,
				 const char *func, int line)
{
	BT_DBG("chan %p conn %p %s -> %s", chan, chan->conn,
	       bt_iso_chan_state_str(chan->state),
	       bt_iso_chan_state_str(state));

	/* check transitions validness */
	switch (state) {
	case BT_ISO_DISCONNECTED:
	case BT_ISO_BOUND:
		/* regardless of old state always allows these states */
		break;
	case BT_ISO_CONNECT:
		if (chan->state != BT_ISO_BOUND) {
			BT_WARN("%s()%d: invalid transition", func, line);
		}
		break;
	case BT_ISO_CONNECTED:
		if (chan->state != BT_ISO_BOUND &&
		    chan->state != BT_ISO_CONNECT) {
			BT_WARN("%s()%d: invalid transition", func, line);
		}
		break;
	case BT_ISO_DISCONNECT:
		if (chan->state != BT_ISO_CONNECTED) {
			BT_WARN("%s()%d: invalid transition", func, line);
		}
		break;
	default:
		BT_ERR("%s()%d: unknown (%u) state was set", func, line, state);
		return;
	}

	chan->state = state;
}
#else
void bt_iso_chan_set_state(struct bt_iso_chan *chan, uint8_t state)
{
	chan->state = state;
}
#endif /* CONFIG_BT_DEBUG_ISO */

bool bt_iso_chan_remove(struct bt_conn *conn, struct bt_iso_chan *chan)
{
	return sys_slist_find_and_remove(&conn->channels, &chan->node);
}

int bt_iso_chan_bind(struct bt_conn **conns, uint8_t num_conns,
		     struct bt_iso_chan **chans)
{
	struct bt_iso_create_param param;
	int i, err;
	static uint8_t id;

	CHECKIF(!conns || !num_conns || !chans) {
		BT_DBG("Invalid parameters: conns %p num_conns %u chans %p",
		       conns, num_conns, chans);
		return -EINVAL;
	}

	memset(&param, 0, sizeof(param));

	param.id = id++;
	param.num_conns = num_conns;
	param.conns = conns;
	param.chans = chans;

	err = bt_conn_bind_iso(&param);
	if (err) {
		return err;
	}

	/* Bind respective connection to channel */
	for (i = 0; i < num_conns; i++) {
		bt_iso_chan_add(conns[i], chans[i]);
		bt_iso_chan_set_state(chans[i], BT_ISO_BOUND);
	}

	return 0;
}

int bt_iso_chan_unbind(struct bt_iso_chan *chan)
{
	CHECKIF(!chan) {
		BT_DBG("Invalid parameter: chan %p", chan);
		return -EINVAL;
	}

	if (!chan->conn) {
		return -EINVAL;
	}

	if (!bt_iso_chan_remove(chan->conn, chan)) {
		return -ENOENT;
	}

	bt_conn_unref(chan->conn);
	chan->conn = NULL;

	bt_iso_chan_set_state(chan, BT_ISO_DISCONNECTED);

	return 0;
}

int bt_iso_chan_connect(struct bt_iso_chan **chans, uint8_t num_chans)
{
	struct bt_conn *conns[CONFIG_BT_ISO_MAX_CHAN];
	int i, err;

	CHECKIF(!chans || !num_chans) {
		BT_DBG("Invalid parameters: chans %p num_chans %u", chans,
		       num_chans);
		return -EINVAL;
	}

	for (i = 0; i < num_chans; i++) {
		if (!chans[i]->conn) {
			return -ENOTCONN;
		}

		conns[i] = chans[i]->conn;
	}

	err = bt_conn_connect_iso(conns, num_chans);
	if (err) {
		return err;
	}

	for (i = 0; i < num_chans; i++) {
		bt_iso_chan_set_state(chans[i], BT_ISO_CONNECT);
	}

	return 0;
}

int bt_iso_chan_disconnect(struct bt_iso_chan *chan)
{
	CHECKIF(!chan) {
		BT_DBG("Invalid parameter: chan %p", chan);
		return -EINVAL;
	}

	if (!chan->conn) {
		return -ENOTCONN;
	}

	if (chan->state == BT_ISO_BOUND) {
		bt_iso_chan_disconnected(chan, BT_HCI_ERR_LOCALHOST_TERM_CONN);
		return 0;
	}

	return bt_conn_disconnect(chan->conn, BT_HCI_ERR_REMOTE_USER_TERM_CONN);
}

void bt_iso_recv(struct bt_conn *conn, struct net_buf *buf, uint8_t flags)
{
	struct bt_hci_iso_data_hdr *hdr;
	struct bt_iso_chan *chan;
	uint8_t pb, ts;
	uint16_t len, pkt_seq_no;

	pb = bt_iso_flags_pb(flags);
	ts = bt_iso_flags_ts(flags);

	BT_DBG("handle %u len %u flags 0x%02x pb 0x%02x ts 0x%02x",
	       conn->handle, buf->len, flags, pb, ts);

	/* When the PB_Flag does not equal 0b00, the fields Time_Stamp,
	 * Packet_Sequence_Number, Packet_Status_Flag and ISO_SDU_Length
	 * are omitted from the HCI ISO Data packet.
	 */
	switch (pb) {
	case BT_ISO_START:
	case BT_ISO_SINGLE:
		/* The ISO_Data_Load field contains either the first fragment
		 * of an SDU or a complete SDU.
		 */
		if (ts) {
			struct bt_hci_iso_ts_data_hdr *ts_hdr;

			ts_hdr = net_buf_pull_mem(buf, sizeof(*ts_hdr));
			iso_info(buf)->ts = sys_le32_to_cpu(ts_hdr->ts);

			hdr = &ts_hdr->data;
		} else {
			hdr = net_buf_pull_mem(buf, sizeof(*hdr));
			/* TODO: Generate a timestamp? */
			iso_info(buf)->ts = 0x00000000;
		}

		len = sys_le16_to_cpu(hdr->slen);
		flags = bt_iso_pkt_flags(len);
		len = bt_iso_pkt_len(len);
		pkt_seq_no = sys_le16_to_cpu(hdr->sn);
		iso_info(buf)->sn = pkt_seq_no;

		/* TODO: Drop the packet if NOP? */

		BT_DBG("%s, len %u total %u flags 0x%02x timestamp %u",
		       pb == BT_ISO_START ? "Start" : "Single", buf->len, len,
		       flags, iso_info(buf)->ts);

		if (conn->rx) {
			BT_ERR("Unexpected ISO %s fragment",
			       pb == BT_ISO_START ? "Start" : "Single");
			bt_conn_reset_rx_state(conn);
		}

		conn->rx = buf;
		conn->rx_len = len - buf->len;
		if (conn->rx_len) {
			/* if conn->rx_len then package is longer than the
			 * buf->len and cannot fit in a SINGLE package
			 */
			if (pb == BT_ISO_SINGLE) {
				BT_ERR("Unexpected ISO single fragment");
				bt_conn_reset_rx_state(conn);
			}
			return;
		}
		break;

	case BT_ISO_CONT:
		/* The ISO_Data_Load field contains a continuation fragment of
		 * an SDU.
		 */
		if (!conn->rx) {
			BT_ERR("Unexpected ISO continuation fragment");
			net_buf_unref(buf);
			return;
		}

		BT_DBG("Cont, len %u rx_len %u", buf->len, conn->rx_len);

		if (buf->len > net_buf_tailroom(conn->rx)) {
			BT_ERR("Not enough buffer space for ISO data");
			bt_conn_reset_rx_state(conn);
			net_buf_unref(buf);
			return;
		}

		net_buf_add_mem(conn->rx, buf->data, buf->len);
		conn->rx_len -= buf->len;
		net_buf_unref(buf);
		return;

	case BT_ISO_END:
		/* The ISO_Data_Load field contains the last fragment of an
		 * SDU.
		 */
		BT_DBG("End, len %u rx_len %u", buf->len, conn->rx_len);

		if (!conn->rx) {
			BT_ERR("Unexpected ISO end fragment");
			net_buf_unref(buf);
			return;
		}

		if (buf->len > net_buf_tailroom(conn->rx)) {
			BT_ERR("Not enough buffer space for ISO data");
			bt_conn_reset_rx_state(conn);
			net_buf_unref(buf);
			return;
		}

		net_buf_add_mem(conn->rx, buf->data, buf->len);
		conn->rx_len -= buf->len;
		net_buf_unref(buf);

		break;
	default:
		BT_ERR("Unexpected ISO pb flags (0x%02x)", pb);
		bt_conn_reset_rx_state(conn);
		net_buf_unref(buf);
		return;
	}

	SYS_SLIST_FOR_EACH_CONTAINER(&conn->channels, chan, node) {
		if (chan->ops->recv) {
			chan->ops->recv(chan, iso_info(conn->rx), conn->rx);
		}
	}

	bt_conn_reset_rx_state(conn);
}

int bt_iso_chan_send(struct bt_iso_chan *chan, struct net_buf *buf)
{
	struct bt_hci_iso_data_hdr *hdr;
	static uint16_t sn;

	CHECKIF(!chan || !buf) {
		BT_DBG("Invalid parameters: chan %p buf %p", chan, buf);
		return -EINVAL;
	}

	BT_DBG("chan %p len %zu", chan, net_buf_frags_len(buf));

	if (!chan->conn) {
		BT_DBG("Not connected");
		return -ENOTCONN;
	}

	hdr = net_buf_push(buf, sizeof(*hdr));
	hdr->sn = sys_cpu_to_le16(sn++);
	hdr->slen = sys_cpu_to_le16(bt_iso_pkt_len_pack(net_buf_frags_len(buf)
							- sizeof(*hdr),
							BT_ISO_DATA_VALID));

	return bt_conn_send(chan->conn, buf);
}

struct bt_conn_iso *bt_conn_iso(struct bt_conn *conn)
{
	CHECKIF(!conn || conn->type != BT_CONN_TYPE_ISO) {
		BT_DBG("Invalid parameters: conn %p conn->type %u", conn,
		       conn ? conn->type : 0);
		return NULL;
	}

	return &conn->iso;
}

#if defined(CONFIG_BT_ISO_BROADCAST)

static struct bt_iso_big *get_free_big(void)
{
	/* We can use the index in the `bigs` array as BIG handles, for both
	 * broadcaster and receiver (even if the device is both!)
	 */

	for (int i = 0; i < ARRAY_SIZE(bigs); i++) {
		if (!atomic_test_and_set_bit(bigs[i].flags, BT_BIG_INITIALIZED)) {
			bigs[i].handle = i;
			return &bigs[i];
		}
	}

	BT_DBG("Could not allocate any more BIGs");

	return NULL;
}

static struct bt_iso_big *big_lookup_flag(int bit)
{
	for (int i = 0; i < ARRAY_SIZE(bigs); i++) {
		if (atomic_test_bit(bigs[i].flags, bit)) {
			return &bigs[i];
		}
	}

	BT_DBG("No BIG with flag bit %d set", bit);

	return NULL;
}

static void cleanup_big(struct bt_iso_big *big)
{
	for (int i = 0; i < big->num_bis; i++) {
		struct bt_iso_chan *bis = big->bis[i];

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

	memset(big, 0, sizeof(*big));
}

static void big_disconnect(struct bt_iso_big *big, uint8_t reason)
{
	for (int i = 0; i < big->num_bis; i++) {
		big->bis[i]->conn->err = reason;

		bt_iso_disconnected(big->bis[i]->conn);
	}
}

static int big_init_bis(struct bt_iso_big *big, bool broadcaster)
{
	for (int i = 0; i < big->num_bis; i++) {
		struct bt_iso_chan *bis = big->bis[i];

		if (!bis) {
			BT_DBG("BIS was NULL");
			return -EINVAL;
		}

		if (bis->conn) {
			BT_DBG("BIS conn was already allocated");
			return -EALREADY;
		}

		if (!bis->qos || (!bis->qos->tx && broadcaster)) {
			BT_DBG("BIS QOS was invalid");
			return -EINVAL;
		}

		bis->conn = iso_new();

		if (!bis->conn) {
			BT_ERR("Unable to allocate BIS connection");
			return -ENOMEM;
		}

		bis->conn->iso.big_handle = big->handle;
		bis->conn->iso.is_bis = true;
		bis->conn->iso.bis_id = bt_conn_index(bis->conn);

		bt_iso_chan_add(bis->conn, bis);
		bt_iso_chan_set_state(bis, BT_ISO_BOUND);
	}

	return 0;
}

static int hci_le_create_big(struct bt_le_ext_adv *padv, struct bt_iso_big *big,
			     struct bt_iso_big_create_param *param)
{
	struct bt_hci_cp_le_create_big *req;
	struct bt_hci_cmd_state_set state;
	struct net_buf *buf;
	int err;
	static struct bt_iso_chan_qos *qos;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_CREATE_BIG, sizeof(*req));

	if (!buf) {
		return -ENOBUFS;
	}

	/* All BIS will share the same QOS */
	qos = big->bis[0]->qos;

	req = net_buf_add(buf, sizeof(*req));
	req->big_handle = big->handle;
	req->adv_handle = padv->handle;
	req->num_bis = big->num_bis;
	sys_put_le24(qos->tx->interval, req->sdu_interval);
	req->max_sdu = sys_cpu_to_le16(qos->tx->sdu);
	req->max_latency = sys_cpu_to_le16(qos->tx->latency);
	req->rtn = qos->tx->rtn;
	req->phy = qos->tx->phy;
	req->packing = qos->packing;
	req->framing = qos->framing;
	req->encryption = param->encryption;
	if (req->encryption) {
		memcpy(req->bcode, param->bcode, sizeof(req->bcode));
	} else {
		memset(req->bcode, 0, sizeof(req->bcode));
	}

	bt_hci_cmd_state_set_init(buf, &state, big->flags, BT_BIG_PENDING, true);
	err = bt_hci_cmd_send_sync(BT_HCI_OP_LE_CREATE_BIG, buf, NULL);

	if (err) {
		return err;
	}

	for (int i = 0; i < big->num_bis; i++) {
		bt_iso_chan_set_state(big->bis[i], BT_ISO_CONNECT);
	}
	return err;
}

int bt_iso_big_create(struct bt_le_ext_adv *padv, struct bt_iso_big_create_param *param,
		      struct bt_iso_big **out_big)
{
	int err;
	struct bt_iso_big *big;

	if (!atomic_test_bit(padv->flags, BT_PER_ADV_PARAMS_SET)) {
		BT_DBG("PA params not set; invalid adv object");
		return -EINVAL;
	}

	CHECKIF(!param->bis_channels) {
		BT_DBG("NULL BIS channels");
		return -EINVAL;
	}

	CHECKIF(!param->num_bis) {
		BT_DBG("Invalid number of BIS %u", param->num_bis);
		return -EINVAL;
	}

	big = get_free_big();

	if (!big) {
		return -ENOMEM;
	}

	big->bis = param->bis_channels;
	big->num_bis = param->num_bis;

	err = big_init_bis(big, true);
	if (err) {
		BT_DBG("Could not init BIG %d", err);
		cleanup_big(big);
		return err;
	}

	err = hci_le_create_big(padv, big, param);
	if (err) {
		BT_DBG("Could not create BIG %d", err);
		cleanup_big(big);
		return err;
	}

	*out_big = big;

	return err;
}

static int hci_le_terminate_big(struct bt_iso_big *big)
{
	struct bt_hci_cp_le_terminate_big *req;
	struct net_buf *buf;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_TERMINATE_BIG, sizeof(*req));
	if (!buf) {
		return -ENOBUFS;
	}

	req = net_buf_add(buf, sizeof(*req));
	req->big_handle = big->handle;
	req->reason = BT_HCI_ERR_REMOTE_USER_TERM_CONN;

	return bt_hci_cmd_send_sync(BT_HCI_OP_LE_TERMINATE_BIG, buf, NULL);
}

static int hci_le_big_sync_term(struct bt_iso_big *big)
{
	struct bt_hci_cp_le_big_terminate_sync *req;
	struct bt_hci_rp_le_big_terminate_sync *evt;
	struct net_buf *buf;
	struct net_buf *rsp;
	int err;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_BIG_TERMINATE_SYNC, sizeof(*req));
	if (!buf) {
		return -ENOBUFS;
	}

	req = net_buf_add(buf, sizeof(*req));
	req->big_handle = big->handle;
	err = bt_hci_cmd_send_sync(BT_HCI_OP_LE_BIG_TERMINATE_SYNC, buf, &rsp);
	if (err) {
		return err;
	}

	evt = (struct bt_hci_rp_le_big_terminate_sync *)rsp->data;
	if (evt->status || (evt->big_handle != big->handle)) {
		err = -EIO;
	}

	net_buf_unref(rsp);

	return err;
}

int bt_iso_big_terminate(struct bt_iso_big *big)
{
	int err;
	bool broadcaster;

	if (!atomic_test_bit(big->flags, BT_BIG_INITIALIZED) || !big->num_bis || !big->bis) {
		BT_DBG("BIG not initialized");
		return -EINVAL;
	}

	for (int i = 0; i < big->num_bis; i++) {
		if (!big->bis[i]) {
			BT_DBG("BIG BIS[%d] not initialized", i);
			return -EINVAL;
		}
	}

	/* They all have the same QOS dir so we can just check the first */
	broadcaster = big->bis[0]->qos->tx ? true : false;

	if (broadcaster) {
		err = hci_le_terminate_big(big);

		/* Wait for BT_HCI_EVT_LE_BIG_TERMINATE before cleaning up
		 * the BIG in hci_le_big_terminate
		 */
		if (!err) {
			for (int i = 0; i < big->num_bis; i++) {
				bt_iso_chan_set_state(big->bis[i], BT_ISO_DISCONNECT);
			}
		}
	} else {
		err = hci_le_big_sync_term(big);

		if (!err) {
			big_disconnect(big, BT_HCI_ERR_LOCALHOST_TERM_CONN);
			cleanup_big(big);
		}
	}

	if (err) {
		BT_DBG("Could not terminate BIG %d", err);
	}

	return err;
}

void hci_le_big_complete(struct net_buf *buf)
{
	struct bt_hci_evt_le_big_complete *evt = (void *)buf->data;
	struct bt_iso_big *big;

	if (evt->big_handle >= ARRAY_SIZE(bigs)) {
		BT_WARN("Invalid BIG handle");

		big = big_lookup_flag(BT_BIG_PENDING);
		if (big) {
			big_disconnect(big, evt->status ? evt->status : BT_HCI_ERR_UNSPECIFIED);
			cleanup_big(big);
		}

		return;
	}

	big = &bigs[evt->big_handle];
	atomic_clear_bit(big->flags, BT_BIG_PENDING);

	BT_DBG("BIG[%u] %p completed, status %u", big->handle, big, evt->status);

	if (evt->status || evt->num_bis != big->num_bis) {
		if (evt->status == BT_HCI_ERR_SUCCESS && evt->num_bis != big->num_bis) {
			BT_ERR("Invalid number of BIS created, was %u expected %u",
			       evt->num_bis, big->num_bis);
		}
		big_disconnect(big, evt->status ? evt->status : BT_HCI_ERR_UNSPECIFIED);
		cleanup_big(big);
		return;
	}

	for (int i = 0; i < big->num_bis; i++) {
		struct bt_iso_chan *bis = big->bis[i];

		bis->conn->handle = sys_le16_to_cpu(evt->handle[i]);
		bt_conn_set_state(bis->conn, BT_CONN_CONNECTED);
	}
}

void hci_le_big_terminate(struct net_buf *buf)
{
	struct bt_hci_evt_le_big_terminate *evt = (void *)buf->data;
	struct bt_iso_big *big;

	if (evt->big_handle >= ARRAY_SIZE(bigs)) {
		BT_WARN("Invalid BIG handle");
		return;
	}

	big = &bigs[evt->big_handle];

	BT_DBG("BIG[%u] %p terminated", big->handle, big);

	big_disconnect(big, evt->reason);
	cleanup_big(big);
}

void hci_le_big_sync_established(struct net_buf *buf)
{
	struct bt_hci_evt_le_big_sync_established *evt = (void *)buf->data;
	struct bt_iso_big *big;

	if (evt->big_handle >= ARRAY_SIZE(bigs)) {
		BT_WARN("Invalid BIG handle");
		big = big_lookup_flag(BT_BIG_SYNCING);
		if (big) {
			big_disconnect(big, evt->status ? evt->status : BT_HCI_ERR_UNSPECIFIED);
			cleanup_big(big);
		}

		return;
	}

	big = &bigs[evt->big_handle];
	atomic_clear_bit(big->flags, BT_BIG_SYNCING);

	BT_DBG("BIG[%u] %p sync established, status %u", big->handle, big, evt->status);

	if (evt->status || evt->num_bis != big->num_bis) {
		if (evt->status == BT_HCI_ERR_SUCCESS && evt->num_bis != big->num_bis) {
			BT_ERR("Invalid number of BIS synced, was %u expected %u",
			       evt->num_bis, big->num_bis);
		}
		big_disconnect(big, evt->status ? evt->status : BT_HCI_ERR_UNSPECIFIED);
		cleanup_big(big);
		return;
	}

	for (int i = 0; i < big->num_bis; i++) {
		struct bt_iso_chan *bis = big->bis[i];
		uint16_t bis_handle = sys_le16_to_cpu(evt->handle[i]);

		bis->conn->handle = bis_handle;

		bt_conn_set_state(bis->conn, BT_CONN_CONNECTED);
	}

	/* TODO: Deal with the rest of the fields in the event,
	 * if it makes sense
	 */
}

void hci_le_big_sync_lost(struct net_buf *buf)
{
	struct bt_hci_evt_le_big_sync_lost *evt = (void *)buf->data;
	struct bt_iso_big *big;

	if (evt->big_handle >= ARRAY_SIZE(bigs)) {
		BT_WARN("Invalid BIG handle");
		return;
	}

	big = &bigs[evt->big_handle];

	BT_DBG("BIG[%u] %p sync lost", big->handle, big);

	big_disconnect(big, evt->reason);
	cleanup_big(big);
}

static int hci_le_big_create_sync(const struct bt_le_per_adv_sync *sync, struct bt_iso_big *big,
				  const struct bt_iso_big_sync_param *param)
{
	struct bt_hci_cp_le_big_create_sync *req;
	struct bt_hci_cmd_state_set state;
	struct net_buf *buf;
	int err;
	uint8_t bit_idx = 0;

	buf = bt_hci_cmd_create(BT_HCI_OP_LE_BIG_CREATE_SYNC, sizeof(*req) + big->num_bis);
	if (!buf) {
		return -ENOBUFS;
	}

	req = net_buf_add(buf, sizeof(*req) + big->num_bis);
	req->big_handle = big->handle;
	req->sync_handle = sys_cpu_to_le16(sync->handle);
	req->encryption = param->encryption;
	if (req->encryption) {
		memcpy(req->bcode, param->bcode, sizeof(req->bcode));
	} else {
		memset(req->bcode, 0, sizeof(req->bcode));
	}
	req->mse = param->mse;
	req->sync_timeout = sys_cpu_to_le16(param->sync_timeout);
	req->num_bis = big->num_bis;
	/* Transform from bitfield to array */
	for (int i = 0; i < 0x1F; i++) {
		if (param->bis_bitfield & BIT(i)) {
			if (bit_idx == big->num_bis) {
				BT_DBG("BIG cannot contain %u BISes", bit_idx + 1);
				return -EINVAL;
			}
			req->bis[bit_idx++] = i + 1; /* indices start from 1 */
		}
	}

	if (bit_idx != big->num_bis) {
		BT_DBG("Number of bits in bis_bitfield (%u) doesn't match num_bis (%u)",
		       bit_idx, big->num_bis);
		return -EINVAL;
	}

	bt_hci_cmd_state_set_init(buf, &state, big->flags, BT_BIG_SYNCING, true);
	err = bt_hci_cmd_send_sync(BT_HCI_OP_LE_BIG_CREATE_SYNC, buf, NULL);

	return err;
}

int bt_iso_big_sync(struct bt_le_per_adv_sync *sync, struct bt_iso_big_sync_param *param,
		    struct bt_iso_big **out_big)
{
	int err;
	struct bt_iso_big *big;

	if (!atomic_test_bit(sync->flags, BT_PER_ADV_SYNC_SYNCED)) {
		BT_DBG("PA sync not synced");
		return -EINVAL;
	}

	CHECKIF(param->mse > 0x1F) {
		BT_DBG("Invalid MSE 0x%02x", param->mse);
		return -EINVAL;
	}

	CHECKIF(param->sync_timeout < 0x000A || param->sync_timeout > 0x4000) {
		BT_DBG("Invalid sync timeout 0x%04x", param->sync_timeout);
		return -EINVAL;
	}

	CHECKIF(!param->bis_bitfield) {
		BT_DBG("Invalid BIS bitfield 0x%08x", param->bis_bitfield);
		return -EINVAL;
	}

	CHECKIF(!param->bis_channels) {
		BT_DBG("NULL BIS channels");
		return -EINVAL;
	}

	CHECKIF(!param->num_bis) {
		BT_DBG("Invalid number of BIS %u", param->num_bis);
		return -EINVAL;
	}

	big = get_free_big();

	if (!big) {
		return -ENOMEM;
	}

	big->bis = param->bis_channels;
	big->num_bis = param->num_bis;

	err = big_init_bis(big, false);
	if (err) {
		BT_DBG("Could not init BIG %d", err);
		cleanup_big(big);
		return err;
	}

	err = hci_le_big_create_sync(sync, big, param);
	if (err) {
		BT_DBG("Could not create BIG sync %d", err);
		cleanup_big(big);
		return err;
	}

	for (int i = 0; i < big->num_bis; i++) {
		bt_iso_chan_set_state(big->bis[i], BT_ISO_CONNECT);
	}

	*out_big = big;

	return 0;
}
#endif /* defined(CONFIG_BT_ISO_BROADCAST) */
