/*
 * Copyright (c) 2022 Nordic Semiconductor ASA
 *
 * SPDX-License-Identifier: Apache-2.0
 */

#include <errno.h>
#include <zephyr/kernel.h>
#include <zephyr/usb/usbd.h>
#include <zephyr/drivers/usb/udc.h>
#include <zephyr/sys/byteorder.h>
#include <zephyr/sys/slist.h>

#include "usbd_device.h"
#include "usbd_desc.h"
#include "usbd_ch9.h"
#include "usbd_config.h"
#include "usbd_class.h"
#include "usbd_class_api.h"
#include "usbd_interface.h"

#include <zephyr/logging/log.h>
LOG_MODULE_REGISTER(usbd_ch9, CONFIG_USBD_LOG_LEVEL);

#define CTRL_AWAIT_SETUP_DATA		0
#define CTRL_AWAIT_STATUS_STAGE		1

static bool reqtype_is_to_host(const struct usb_setup_packet *const setup)
{
	return setup->wLength && USB_REQTYPE_GET_DIR(setup->bmRequestType);
}

static bool reqtype_is_to_device(const struct usb_setup_packet *const setup)
{
	return !reqtype_is_to_host(setup);
}

static void ch9_set_ctrl_type(struct usbd_contex *const uds_ctx,
				   const int type)
{
	uds_ctx->ch9_data.ctrl_type = type;
}

static int ch9_get_ctrl_type(struct usbd_contex *const uds_ctx)
{
	return uds_ctx->ch9_data.ctrl_type;
}

static int set_address_after_status_stage(struct usbd_contex *const uds_ctx)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	int ret;

	ret = udc_set_address(uds_ctx->dev, setup->wValue);
	if (ret) {
		LOG_ERR("Failed to set device address 0x%x", setup->wValue);
		return ret;
	}

	uds_ctx->ch9_data.new_address = false;

	return ret;
}

static int sreq_set_address(struct usbd_contex *const uds_ctx)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);

	/* Not specified if wLength is non-zero, treat as error */
	if (setup->wValue > 127 || setup->wLength) {
		errno = -ENOTSUP;
		return 0;
	}

	if (setup->RequestType.recipient != USB_REQTYPE_RECIPIENT_DEVICE) {
		errno = -ENOTSUP;
		return 0;
	}

	if (usbd_state_is_configured(uds_ctx)) {
		errno = -EPERM;
		return 0;
	}

	uds_ctx->ch9_data.new_address = true;
	if (usbd_state_is_address(uds_ctx) && setup->wValue == 0) {
		uds_ctx->ch9_data.state = USBD_STATE_DEFAULT;
	} else {
		uds_ctx->ch9_data.state = USBD_STATE_ADDRESS;
	}


	return 0;
}

static int sreq_set_configuration(struct usbd_contex *const uds_ctx)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	int ret;

	LOG_INF("Set Configuration Request value %u", setup->wValue);

	/* Not specified if wLength is non-zero, treat as error */
	if (setup->wValue > UINT8_MAX || setup->wLength) {
		errno = -ENOTSUP;
		return 0;
	}

	if (setup->RequestType.recipient != USB_REQTYPE_RECIPIENT_DEVICE) {
		errno = -ENOTSUP;
		return 0;
	}

	if (usbd_state_is_default(uds_ctx)) {
		errno = -EPERM;
		return 0;
	}

	if (setup->wValue && !usbd_config_exist(uds_ctx, setup->wValue)) {
		errno = -EPERM;
		return 0;
	}

	if (setup->wValue == usbd_get_config_value(uds_ctx)) {
		LOG_DBG("Already in the configuration %u", setup->wValue);
		return 0;
	}

	ret = usbd_config_set(uds_ctx, setup->wValue);
	if (ret) {
		LOG_ERR("Failed to set configuration %u, %d",
			setup->wValue, ret);
		return ret;
	}

	if (setup->wValue == 0) {
		/* Enter address state */
		uds_ctx->ch9_data.state = USBD_STATE_ADDRESS;
	} else {
		uds_ctx->ch9_data.state = USBD_STATE_CONFIGURED;
	}

	return ret;
}

static int sreq_set_interface(struct usbd_contex *const uds_ctx)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	int ret;

	if (setup->RequestType.recipient != USB_REQTYPE_RECIPIENT_INTERFACE) {
		errno = -ENOTSUP;
		return 0;
	}

	/* Not specified if wLength is non-zero, treat as error */
	if (setup->wLength) {
		errno = -ENOTSUP;
		return 0;
	}

	if (setup->wValue > UINT8_MAX || setup->wIndex > UINT8_MAX) {
		errno = -ENOTSUP;
		return 0;
	}

	if (!usbd_state_is_configured(uds_ctx)) {
		errno = -EPERM;
		return 0;
	}

	ret = usbd_interface_set(uds_ctx, setup->wIndex, setup->wValue);
	if (ret == -ENOENT) {
		LOG_INF("Interface or alternate does not exist");
		errno = ret;
		ret = 0;
	}

	return ret;
}

static void sreq_feature_halt_notify(struct usbd_contex *const uds_ctx,
				     const uint8_t ep, const bool halted)
{
	struct usbd_class_node *c_nd = usbd_class_get_by_ep(uds_ctx, ep);

	if (c_nd != NULL) {
		usbd_class_feature_halt(c_nd, ep, halted);
	}
}

static int sreq_clear_feature(struct usbd_contex *const uds_ctx)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	uint8_t ep = setup->wIndex;
	int ret = 0;

	/* Not specified if wLength is non-zero, treat as error */
	if (setup->wLength) {
		errno = -ENOTSUP;
		return 0;
	}

	/* Not specified in default state, treat as error */
	if (usbd_state_is_default(uds_ctx)) {
		errno = -EPERM;
		return 0;
	}

	if (usbd_state_is_address(uds_ctx) && setup->wIndex) {
		errno = -EPERM;
		return 0;
	}

	switch (setup->RequestType.recipient) {
	case USB_REQTYPE_RECIPIENT_DEVICE:
		if (setup->wIndex != 0) {
			errno = -EPERM;
			return 0;
		}

		if (setup->wValue == USB_SFS_REMOTE_WAKEUP) {
			LOG_DBG("Clear feature remote wakeup");
			uds_ctx->status.rwup = false;
		}
		break;
	case USB_REQTYPE_RECIPIENT_ENDPOINT:
		if (setup->wValue == USB_SFS_ENDPOINT_HALT) {
			/* UDC checks if endpoint is enabled */
			errno = usbd_ep_clear_halt(uds_ctx, ep);
			ret = (errno == -EPERM) ? errno : 0;
			if (ret == 0) {
				/* Notify class instance */
				sreq_feature_halt_notify(uds_ctx, ep, false);
			}
			break;
		}
		break;
	case USB_REQTYPE_RECIPIENT_INTERFACE:
	default:
		break;
	}

	return ret;
}

static int sreq_set_feature(struct usbd_contex *const uds_ctx)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	uint8_t ep = setup->wIndex;
	int ret = 0;

	/* Not specified if wLength is non-zero, treat as error */
	if (setup->wLength) {
		errno = -ENOTSUP;
		return 0;
	}

	/*
	 * TEST_MODE is not supported yet, other are not specified
	 * in default state, treat as error.
	 */
	if (usbd_state_is_default(uds_ctx)) {
		errno = -EPERM;
		return 0;
	}

	if (usbd_state_is_address(uds_ctx) && setup->wIndex) {
		errno = -EPERM;
		return 0;
	}

	switch (setup->RequestType.recipient) {
	case USB_REQTYPE_RECIPIENT_DEVICE:
		if (setup->wIndex != 0) {
			errno = -EPERM;
			return 0;
		}

		if (setup->wValue == USB_SFS_REMOTE_WAKEUP) {
			LOG_DBG("Set feature remote wakeup");
			uds_ctx->status.rwup = true;
		}
		break;
	case USB_REQTYPE_RECIPIENT_ENDPOINT:
		if (setup->wValue == USB_SFS_ENDPOINT_HALT) {
			/* UDC checks if endpoint is enabled */
			errno = usbd_ep_set_halt(uds_ctx, ep);
			ret = (errno == -EPERM) ? errno : 0;
			if (ret == 0) {
				/* Notify class instance */
				sreq_feature_halt_notify(uds_ctx, ep, true);
			}
			break;
		}
		break;
	case USB_REQTYPE_RECIPIENT_INTERFACE:
	default:
		break;
	}

	return ret;
}

static int std_request_to_device(struct usbd_contex *const uds_ctx,
				 struct net_buf *const buf)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	int ret;

	switch (setup->bRequest) {
	case USB_SREQ_SET_ADDRESS:
		ret = sreq_set_address(uds_ctx);
		break;
	case USB_SREQ_SET_CONFIGURATION:
		ret = sreq_set_configuration(uds_ctx);
		break;
	case USB_SREQ_SET_INTERFACE:
		ret = sreq_set_interface(uds_ctx);
		break;
	case USB_SREQ_CLEAR_FEATURE:
		ret = sreq_clear_feature(uds_ctx);
		break;
	case USB_SREQ_SET_FEATURE:
		ret = sreq_set_feature(uds_ctx);
		break;
	default:
		errno = -ENOTSUP;
		ret = 0;
		break;
	}

	return ret;
}

static int sreq_get_status(struct usbd_contex *const uds_ctx,
			   struct net_buf *const buf)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	uint8_t ep = setup->wIndex;
	uint16_t response = 0;

	if (setup->wLength != sizeof(response)) {
		errno = -ENOTSUP;
		return 0;
	}

	/* Not specified in default state, treat as error */
	if (usbd_state_is_default(uds_ctx)) {
		errno = -EPERM;
		return 0;
	}

	if (usbd_state_is_address(uds_ctx) && setup->wIndex) {
		errno = -EPERM;
		return 0;
	}

	switch (setup->RequestType.recipient) {
	case USB_REQTYPE_RECIPIENT_DEVICE:
		if (setup->wIndex != 0) {
			errno = -EPERM;
			return 0;
		}

		response = uds_ctx->status.rwup ?
			   USB_GET_STATUS_REMOTE_WAKEUP : 0;
		break;
	case USB_REQTYPE_RECIPIENT_ENDPOINT:
		response = usbd_ep_is_halted(uds_ctx, ep) ? BIT(0) : 0;
		break;
	case USB_REQTYPE_RECIPIENT_INTERFACE:
		/* Response is always reset to zero.
		 * TODO: add check if interface exist?
		 */
		break;
	default:
		break;
	}

	if (net_buf_tailroom(buf) < setup->wLength) {
		errno = -ENOMEM;
		return 0;
	}

	LOG_DBG("Get Status response 0x%04x", response);
	net_buf_add_le16(buf, response);

	return 0;
}

static int sreq_get_desc_cfg(struct usbd_contex *const uds_ctx,
			     struct net_buf *const buf,
			     const uint8_t idx)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	struct usb_cfg_descriptor *cfg_desc;
	struct usbd_config_node *cfg_nd;
	struct usbd_class_node *c_nd;
	uint16_t len;

	cfg_nd = usbd_config_get(uds_ctx, idx + 1);
	if (cfg_nd == NULL) {
		LOG_ERR("Configuration descriptor %u not found", idx + 1);
		errno = -ENOTSUP;
		return 0;
	}

	cfg_desc = cfg_nd->desc;
	len = MIN(setup->wLength, net_buf_tailroom(buf));
	net_buf_add_mem(buf, cfg_desc, MIN(len, cfg_desc->bLength));

	SYS_SLIST_FOR_EACH_CONTAINER(&cfg_nd->class_list, c_nd, node) {
		struct usb_desc_header *head = c_nd->data->desc;
		size_t desc_len = usbd_class_desc_len(c_nd);

		len = MIN(setup->wLength, net_buf_tailroom(buf));
		net_buf_add_mem(buf, head, MIN(len, desc_len));
	}

	LOG_DBG("Get Configuration descriptor %u, len %u", idx, buf->len);

	return 0;
}

static int sreq_get_desc(struct usbd_contex *const uds_ctx,
			 struct net_buf *const buf,
			 const uint8_t type, const uint8_t idx)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	struct usb_desc_header *head;
	size_t len;

	if (type == USB_DESC_DEVICE) {
		head = uds_ctx->desc;
	} else {
		head = usbd_get_descriptor(uds_ctx, type, idx);
	}

	if (head == NULL) {
		errno = -ENOTSUP;
		return 0;
	}

	len = MIN(setup->wLength, net_buf_tailroom(buf));
	net_buf_add_mem(buf, head, MIN(len, head->bLength));

	return 0;
}

static int sreq_get_descriptor(struct usbd_contex *const uds_ctx,
			       struct net_buf *const buf)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	uint8_t desc_type = USB_GET_DESCRIPTOR_TYPE(setup->wValue);
	uint8_t desc_idx = USB_GET_DESCRIPTOR_INDEX(setup->wValue);

	LOG_DBG("Get Descriptor request type %u index %u",
		desc_type, desc_idx);

	switch (desc_type) {
	case USB_DESC_DEVICE:
		return sreq_get_desc(uds_ctx, buf, USB_DESC_DEVICE, 0);
	case USB_DESC_CONFIGURATION:
		return sreq_get_desc_cfg(uds_ctx, buf, desc_idx);
	case USB_DESC_STRING:
		return sreq_get_desc(uds_ctx, buf, USB_DESC_STRING, desc_idx);
	case USB_DESC_INTERFACE:
	case USB_DESC_ENDPOINT:
	case USB_DESC_OTHER_SPEED:
	default:
		break;
	}

	errno = -ENOTSUP;
	return 0;
}

static int sreq_get_configuration(struct usbd_contex *const uds_ctx,
				  struct net_buf *const buf)

{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	uint8_t cfg = usbd_get_config_value(uds_ctx);

	/* Not specified in default state, treat as error */
	if (usbd_state_is_default(uds_ctx)) {
		errno = -EPERM;
		return 0;
	}

	if (setup->wLength != sizeof(cfg)) {
		errno = -ENOTSUP;
		return 0;
	}

	if (net_buf_tailroom(buf) < setup->wLength) {
		errno = -ENOMEM;
		return 0;
	}

	net_buf_add_u8(buf, cfg);

	return 0;
}

static int sreq_get_interface(struct usbd_contex *const uds_ctx,
			      struct net_buf *const buf)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	struct usb_cfg_descriptor *cfg_desc;
	struct usbd_config_node *cfg_nd;
	uint8_t cur_alt;

	if (setup->RequestType.recipient != USB_REQTYPE_RECIPIENT_INTERFACE) {
		errno = -EPERM;
		return 0;
	}

	cfg_nd = usbd_config_get_current(uds_ctx);
	cfg_desc = cfg_nd->desc;

	if (setup->wIndex > UINT8_MAX ||
	    setup->wIndex > cfg_desc->bNumInterfaces) {
		errno = -ENOTSUP;
		return 0;
	}

	if (usbd_get_alt_value(uds_ctx, setup->wIndex, &cur_alt)) {
		errno = -ENOTSUP;
		return 0;
	}

	LOG_DBG("Get Interfaces %u, alternate %u",
		setup->wIndex, cur_alt);

	if (setup->wLength != sizeof(cur_alt)) {
		errno = -ENOTSUP;
		return 0;
	}

	if (net_buf_tailroom(buf) < setup->wLength) {
		errno = -ENOMEM;
		return 0;
	}

	net_buf_add_u8(buf, cur_alt);

	return 0;
}

static int std_request_to_host(struct usbd_contex *const uds_ctx,
			       struct net_buf *const buf)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	int ret;

	switch (setup->bRequest) {
	case USB_SREQ_GET_STATUS:
		ret = sreq_get_status(uds_ctx, buf);
		break;
	case USB_SREQ_GET_DESCRIPTOR:
		ret = sreq_get_descriptor(uds_ctx, buf);
		break;
	case USB_SREQ_GET_CONFIGURATION:
		ret = sreq_get_configuration(uds_ctx, buf);
		break;
	case USB_SREQ_GET_INTERFACE:
		ret = sreq_get_interface(uds_ctx, buf);
		break;
	default:
		errno = -ENOTSUP;
		ret = 0;
		break;
	}

	return ret;
}

static int nonstd_request(struct usbd_contex *const uds_ctx,
			  struct net_buf *const dbuf)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	struct usbd_class_node *c_nd = NULL;
	int ret = 0;

	switch (setup->RequestType.recipient) {
	case USB_REQTYPE_RECIPIENT_ENDPOINT:
		c_nd = usbd_class_get_by_ep(uds_ctx, setup->wIndex);
		break;
	case USB_REQTYPE_RECIPIENT_INTERFACE:
		c_nd = usbd_class_get_by_iface(uds_ctx, setup->wIndex);
		break;
	case USB_REQTYPE_RECIPIENT_DEVICE:
		c_nd = usbd_class_get_by_req(uds_ctx, setup->bRequest);
		break;
	default:
		break;
	}

	if (c_nd != NULL) {
		if (reqtype_is_to_device(setup)) {
			ret = usbd_class_control_to_dev(c_nd, setup, dbuf);
		} else {
			ret = usbd_class_control_to_host(c_nd, setup, dbuf);
		}
	} else {
		errno = -ENOTSUP;
	}

	return ret;
}

static int handle_setup_request(struct usbd_contex *const uds_ctx,
				struct net_buf *const buf)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	int ret;

	errno = 0;

	switch (setup->RequestType.type) {
	case USB_REQTYPE_TYPE_STANDARD:
		if (reqtype_is_to_device(setup)) {
			ret = std_request_to_device(uds_ctx, buf);
		} else {
			ret = std_request_to_host(uds_ctx, buf);
		}
		break;
	case USB_REQTYPE_TYPE_CLASS:
	case USB_REQTYPE_TYPE_VENDOR:
		ret = nonstd_request(uds_ctx, buf);
		break;
	default:
		errno = -ENOTSUP;
		ret = 0;
	}

	if (errno) {
		LOG_INF("protocol error:");
		LOG_HEXDUMP_INF(setup, sizeof(*setup), "setup:");
		if (errno == -ENOTSUP) {
			LOG_INF("not supported");
		}
		if (errno == -EPERM) {
			LOG_INF("not permitted in device state %u",
				uds_ctx->ch9_data.state);
		}
	}

	return ret;
}

static int ctrl_xfer_get_setup(struct usbd_contex *const uds_ctx,
			       struct net_buf *const buf)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	struct net_buf *buf_b;
	struct udc_buf_info *bi, *bi_b;

	if (buf->len < sizeof(struct usb_setup_packet)) {
		return -EINVAL;
	}

	memcpy(setup, buf->data, sizeof(struct usb_setup_packet));

	setup->wValue = sys_le16_to_cpu(setup->wValue);
	setup->wIndex = sys_le16_to_cpu(setup->wIndex);
	setup->wLength = sys_le16_to_cpu(setup->wLength);

	bi = udc_get_buf_info(buf);

	buf_b = buf->frags;
	if (buf_b == NULL) {
		LOG_ERR("Buffer for data|status is missing");
		return -ENODATA;
	}

	bi_b = udc_get_buf_info(buf_b);

	if (reqtype_is_to_device(setup)) {
		if (setup->wLength) {
			if (!bi_b->data) {
				LOG_ERR("%p is not data", buf_b);
				return -EINVAL;
			}
		} else {
			if (!bi_b->status) {
				LOG_ERR("%p is not status", buf_b);
				return -EINVAL;
			}
		}
	} else {
		if (!setup->wLength) {
			LOG_ERR("device-to-host with wLength zero");
			return -ENOTSUP;
		}

		if (!bi_b->data) {
			LOG_ERR("%p is not data", buf_b);
			return -EINVAL;
		}

	}

	return 0;
}

static struct net_buf *spool_data_out(struct net_buf *const buf)
{
	struct net_buf *next_buf = buf;
	struct udc_buf_info *bi;

	while (next_buf) {
		LOG_INF("spool %p", next_buf);
		next_buf = net_buf_frag_del(NULL, next_buf);
		if (next_buf) {
			bi = udc_get_buf_info(next_buf);
			if (bi->status) {
				return next_buf;
			}
		}
	}

	return NULL;
}

int usbd_handle_ctrl_xfer(struct usbd_contex *const uds_ctx,
			  struct net_buf *const buf, const int err)
{
	struct usb_setup_packet *setup = usbd_get_setup_pkt(uds_ctx);
	struct udc_buf_info *bi;
	int ret = 0;

	bi = udc_get_buf_info(buf);
	if (USB_EP_GET_IDX(bi->ep)) {
		LOG_ERR("Can only handle control requests");
		return -EIO;
	}

	if (err && err != -ENOMEM && !bi->setup) {
		if (err == -ECONNABORTED) {
			LOG_INF("Transfer 0x%02x aborted (bus reset?)", bi->ep);
			net_buf_unref(buf);
			return 0;
		}

		LOG_ERR("Control transfer for 0x%02x has error %d, halt",
			bi->ep, err);
		net_buf_unref(buf);
		return err;
	}

	LOG_INF("Handle control %p ep 0x%02x, len %u, s:%u d:%u s:%u",
		buf, bi->ep, buf->len, bi->setup, bi->data, bi->status);

	if (bi->setup && bi->ep == USB_CONTROL_EP_OUT) {
		struct net_buf *next_buf;

		if (ctrl_xfer_get_setup(uds_ctx, buf)) {
			LOG_ERR("Malformed setup packet");
			net_buf_unref(buf);
			goto ctrl_xfer_stall;
		}

		/* Remove setup packet buffer from the chain */
		next_buf = net_buf_frag_del(NULL, buf);
		if (next_buf == NULL) {
			LOG_ERR("Buffer for data|status is missing");
			goto ctrl_xfer_stall;
		}

		/*
		 * Handle request and data stage, next_buf is either
		 * data+status or status buffers.
		 */
		ret = handle_setup_request(uds_ctx, next_buf);
		if (ret) {
			net_buf_unref(next_buf);
			return ret;
		}

		if (errno) {
			/*
			 * Halt, only protocol errors are recoverable.
			 * Free data stage and linked status stage buffer.
			 */
			net_buf_unref(next_buf);
			goto ctrl_xfer_stall;
		}

		ch9_set_ctrl_type(uds_ctx, CTRL_AWAIT_STATUS_STAGE);
		if (reqtype_is_to_device(setup) && setup->wLength) {
			/* Enqueue STATUS (IN) buffer */
			next_buf = spool_data_out(next_buf);
			if (next_buf == NULL) {
				LOG_ERR("Buffer for status is missing");
				goto ctrl_xfer_stall;
			}

			ret = usbd_ep_ctrl_enqueue(uds_ctx, next_buf);
		} else {
			/* Enqueue DATA (IN) or STATUS (OUT) buffer */
			ret = usbd_ep_ctrl_enqueue(uds_ctx, next_buf);
		}

		return ret;
	}

	if (bi->status && bi->ep == USB_CONTROL_EP_OUT) {
		if (ch9_get_ctrl_type(uds_ctx) == CTRL_AWAIT_STATUS_STAGE) {
			LOG_INF("s-in-status finished");
		} else {
			LOG_WRN("Awaited s-in-status not finished");
		}

		net_buf_unref(buf);

		return 0;
	}

	if (bi->status && bi->ep == USB_CONTROL_EP_IN) {
		net_buf_unref(buf);

		if (ch9_get_ctrl_type(uds_ctx) == CTRL_AWAIT_STATUS_STAGE) {
			LOG_INF("s-(out)-status finished");
			if (unlikely(uds_ctx->ch9_data.new_address)) {
				return set_address_after_status_stage(uds_ctx);
			}
		} else {
			LOG_WRN("Awaited s-(out)-status not finished");
		}

		return ret;
	}

ctrl_xfer_stall:
	/*
	 * Halt only the endpoint over which the host expects
	 * data or status stage. This facilitates the work of the drivers.
	 *
	 * In the case there is -ENOMEM for data OUT stage halt
	 * control OUT endpoint.
	 */
	if (reqtype_is_to_host(setup)) {
		ret = udc_ep_set_halt(uds_ctx->dev, USB_CONTROL_EP_IN);
	} else if (setup->wLength) {
		uint8_t ep = (err == -ENOMEM) ? USB_CONTROL_EP_OUT : USB_CONTROL_EP_IN;

		ret = udc_ep_set_halt(uds_ctx->dev, ep);
	} else {
		ret = udc_ep_set_halt(uds_ctx->dev, USB_CONTROL_EP_IN);
	}

	ch9_set_ctrl_type(uds_ctx, CTRL_AWAIT_SETUP_DATA);

	return ret;
}

int usbd_init_control_pipe(struct usbd_contex *const uds_ctx)
{
	uds_ctx->ch9_data.state = USBD_STATE_DEFAULT;
	ch9_set_ctrl_type(uds_ctx, CTRL_AWAIT_SETUP_DATA);

	return 0;
}
