// SPDX-License-Identifier: GPL-2.0
/*
 * Generation of tables for particular device types
 *
 * Copyright 2019 Google LLC
 * Mostly taken from coreboot file of the same name
 */

#include <common.h>
#include <dm.h>
#include <irq.h>
#include <log.h>
#include <usb.h>
#include <acpi/acpigen.h>
#include <acpi/acpi_device.h>
#include <acpi/acpigen.h>
#include <asm-generic/gpio.h>
#include <dm/acpi.h>

/**
 * acpi_device_path_fill() - Find the root device and build a path from there
 *
 * This recursively reaches back to the root device and progressively adds path
 * elements until the device is reached.
 *
 * @dev: Device to return path of
 * @buf: Buffer to hold the path
 * @buf_len: Length of buffer
 * @cur: Current position in the buffer
 * @return new position in buffer after adding @dev, or -ve on error
 */
static int acpi_device_path_fill(const struct udevice *dev, char *buf,
				 size_t buf_len, int cur)
{
	char name[ACPI_NAME_MAX];
	int next = 0;
	int ret;

	ret = acpi_get_name(dev, name);
	if (ret)
		return ret;

	/*
	 * Make sure this name segment will fit, including the path segment
	 * separator and possible NULL terminator, if this is the last segment.
	 */
	if (cur + strlen(name) + 2 > buf_len)
		return -ENOSPC;

	/* Walk up the tree to the root device */
	if (dev_get_parent(dev)) {
		next = acpi_device_path_fill(dev_get_parent(dev), buf, buf_len,
					     cur);
		if (next < 0)
			return next;
	}

	/* Fill in the path from the root device */
	next += snprintf(buf + next, buf_len - next, "%s%s",
			 dev_get_parent(dev) && *name ? "." : "", name);

	return next;
}

int acpi_device_path(const struct udevice *dev, char *buf, int maxlen)
{
	int ret;

	ret = acpi_device_path_fill(dev, buf, maxlen, 0);
	if (ret < 0)
		return ret;

	return 0;
}

int acpi_device_scope(const struct udevice *dev, char *scope, int maxlen)
{
	int ret;

	if (!dev_get_parent(dev))
		return log_msg_ret("noparent", -EINVAL);

	ret = acpi_device_path_fill(dev_get_parent(dev), scope, maxlen, 0);
	if (ret < 0)
		return log_msg_ret("fill", ret);

	return 0;
}

enum acpi_dev_status acpi_device_status(const struct udevice *dev)
{
	return ACPI_DSTATUS_ALL_ON;
}

/**
 * largeres_write_len_f() - Write a placeholder word value
 *
 * Write a forward length for a large resource (2 bytes)
 *
 * @return pointer to the zero word (for fixing up later)
 */
static void *largeres_write_len_f(struct acpi_ctx *ctx)
{
	u8 *p = acpigen_get_current(ctx);

	acpigen_emit_word(ctx, 0);

	return p;
}

/**
 * largeres_fill_from_len() - Fill in a length value
 *
 * This calculated the number of bytes since the provided @start and writes it
 * to @ptr, which was previous returned by largeres_write_len_f().
 *
 * @ptr: Word to update
 * @start: Start address to count from to calculated the length
 */
static void largeres_fill_from_len(struct acpi_ctx *ctx, char *ptr, u8 *start)
{
	u16 len = acpigen_get_current(ctx) - start;

	ptr[0] = len & 0xff;
	ptr[1] = (len >> 8) & 0xff;
}

/**
 * largeres_fill_len() - Fill in a length value, excluding the length itself
 *
 * Fill in the length field with the value calculated from after the 16bit
 * field to acpigen current. This is useful since the length value does not
 * include the length field itself.
 *
 * This calls acpi_device_largeres_fill_len() passing @ptr + 2 as @start
 *
 * @ptr: Word to update.
 */
static void largeres_fill_len(struct acpi_ctx *ctx, void *ptr)
{
	largeres_fill_from_len(ctx, ptr, ptr + sizeof(u16));
}

/* ACPI 6.3 section 6.4.3.6: Extended Interrupt Descriptor */
static int acpi_device_write_interrupt(struct acpi_ctx *ctx,
				       const struct acpi_irq *irq)
{
	void *desc_length;
	u8 flags;

	if (!irq->pin)
		return -ENOENT;

	/* This is supported by GpioInt() but not Interrupt() */
	if (irq->polarity == ACPI_IRQ_ACTIVE_BOTH)
		return -EINVAL;

	/* Byte 0: Descriptor Type */
	acpigen_emit_byte(ctx, ACPI_DESCRIPTOR_INTERRUPT);

	/* Byte 1-2: Length (filled in later) */
	desc_length = largeres_write_len_f(ctx);

	/*
	 * Byte 3: Flags
	 *  [7:5]: Reserved
	 *    [4]: Wake     (0=NO_WAKE   1=WAKE)
	 *    [3]: Sharing  (0=EXCLUSIVE 1=SHARED)
	 *    [2]: Polarity (0=HIGH      1=LOW)
	 *    [1]: Mode     (0=LEVEL     1=EDGE)
	 *    [0]: Resource (0=PRODUCER  1=CONSUMER)
	 */
	flags = BIT(0); /* ResourceConsumer */
	if (irq->mode == ACPI_IRQ_EDGE_TRIGGERED)
		flags |= BIT(1);
	if (irq->polarity == ACPI_IRQ_ACTIVE_LOW)
		flags |= BIT(2);
	if (irq->shared == ACPI_IRQ_SHARED)
		flags |= BIT(3);
	if (irq->wake == ACPI_IRQ_WAKE)
		flags |= BIT(4);
	acpigen_emit_byte(ctx, flags);

	/* Byte 4: Interrupt Table Entry Count */
	acpigen_emit_byte(ctx, 1);

	/* Byte 5-8: Interrupt Number */
	acpigen_emit_dword(ctx, irq->pin);

	/* Fill in Descriptor Length (account for len word) */
	largeres_fill_len(ctx, desc_length);

	return 0;
}

int acpi_device_write_interrupt_irq(struct acpi_ctx *ctx,
				    const struct irq *req_irq)
{
	struct acpi_irq irq;
	int ret;

	ret = irq_get_acpi(req_irq, &irq);
	if (ret)
		return log_msg_ret("get", ret);
	ret = acpi_device_write_interrupt(ctx, &irq);
	if (ret)
		return log_msg_ret("write", ret);

	return irq.pin;
}

/* ACPI 6.3 section 6.4.3.8.1 - GPIO Interrupt or I/O */
int acpi_device_write_gpio(struct acpi_ctx *ctx, const struct acpi_gpio *gpio)
{
	void *start, *desc_length;
	void *pin_table_offset, *vendor_data_offset, *resource_offset;
	u16 flags = 0;
	int pin;

	if (gpio->type > ACPI_GPIO_TYPE_IO)
		return -EINVAL;

	start = acpigen_get_current(ctx);

	/* Byte 0: Descriptor Type */
	acpigen_emit_byte(ctx, ACPI_DESCRIPTOR_GPIO);

	/* Byte 1-2: Length (fill in later) */
	desc_length = largeres_write_len_f(ctx);

	/* Byte 3: Revision ID */
	acpigen_emit_byte(ctx, ACPI_GPIO_REVISION_ID);

	/* Byte 4: GpioIo or GpioInt */
	acpigen_emit_byte(ctx, gpio->type);

	/*
	 * Byte 5-6: General Flags
	 *   [15:1]: 0 => Reserved
	 *      [0]: 1 => ResourceConsumer
	 */
	acpigen_emit_word(ctx, 1 << 0);

	switch (gpio->type) {
	case ACPI_GPIO_TYPE_INTERRUPT:
		/*
		 * Byte 7-8: GPIO Interrupt Flags
		 *   [15:5]: 0 => Reserved
		 *      [4]: Wake     (0=NO_WAKE   1=WAKE)
		 *      [3]: Sharing  (0=EXCLUSIVE 1=SHARED)
		 *    [2:1]: Polarity (0=HIGH      1=LOW     2=BOTH)
		 *      [0]: Mode     (0=LEVEL     1=EDGE)
		 */
		if (gpio->irq.mode == ACPI_IRQ_EDGE_TRIGGERED)
			flags |= 1 << 0;
		if (gpio->irq.shared == ACPI_IRQ_SHARED)
			flags |= 1 << 3;
		if (gpio->irq.wake == ACPI_IRQ_WAKE)
			flags |= 1 << 4;

		switch (gpio->irq.polarity) {
		case ACPI_IRQ_ACTIVE_HIGH:
			flags |= 0 << 1;
			break;
		case ACPI_IRQ_ACTIVE_LOW:
			flags |= 1 << 1;
			break;
		case ACPI_IRQ_ACTIVE_BOTH:
			flags |= 2 << 1;
			break;
		}
		break;

	case ACPI_GPIO_TYPE_IO:
		/*
		 * Byte 7-8: GPIO IO Flags
		 *   [15:4]: 0 => Reserved
		 *      [3]: Sharing  (0=EXCLUSIVE 1=SHARED)
		 *      [2]: 0 => Reserved
		 *    [1:0]: IO Restriction
		 *           0 => IoRestrictionNone
		 *           1 => IoRestrictionInputOnly
		 *           2 => IoRestrictionOutputOnly
		 *           3 => IoRestrictionNoneAndPreserve
		 */
		flags |= gpio->io_restrict & 3;
		if (gpio->io_shared)
			flags |= 1 << 3;
		break;
	}
	acpigen_emit_word(ctx, flags);

	/*
	 * Byte 9: Pin Configuration
	 *  0x01 => Default (no configuration applied)
	 *  0x02 => Pull-up
	 *  0x03 => Pull-down
	 *  0x04-0x7F => Reserved
	 *  0x80-0xff => Vendor defined
	 */
	acpigen_emit_byte(ctx, gpio->pull);

	/* Byte 10-11: Output Drive Strength in 1/100 mA */
	acpigen_emit_word(ctx, gpio->output_drive_strength);

	/* Byte 12-13: Debounce Timeout in 1/100 ms */
	acpigen_emit_word(ctx, gpio->interrupt_debounce_timeout);

	/* Byte 14-15: Pin Table Offset, relative to start */
	pin_table_offset = largeres_write_len_f(ctx);

	/* Byte 16: Reserved */
	acpigen_emit_byte(ctx, 0);

	/* Byte 17-18: Resource Source Name Offset, relative to start */
	resource_offset = largeres_write_len_f(ctx);

	/* Byte 19-20: Vendor Data Offset, relative to start */
	vendor_data_offset = largeres_write_len_f(ctx);

	/* Byte 21-22: Vendor Data Length */
	acpigen_emit_word(ctx, 0);

	/* Fill in Pin Table Offset */
	largeres_fill_from_len(ctx, pin_table_offset, start);

	/* Pin Table, one word for each pin */
	for (pin = 0; pin < gpio->pin_count; pin++)
		acpigen_emit_word(ctx, gpio->pins[pin]);

	/* Fill in Resource Source Name Offset */
	largeres_fill_from_len(ctx, resource_offset, start);

	/* Resource Source Name String */
	acpigen_emit_string(ctx, gpio->resource);

	/* Fill in Vendor Data Offset */
	largeres_fill_from_len(ctx, vendor_data_offset, start);

	/* Fill in GPIO Descriptor Length (account for len word) */
	largeres_fill_len(ctx, desc_length);

	return gpio->pins[0];
}

int acpi_device_write_gpio_desc(struct acpi_ctx *ctx,
				const struct gpio_desc *desc)
{
	struct acpi_gpio gpio;
	int ret;

	ret = gpio_get_acpi(desc, &gpio);
	if (ret)
		return log_msg_ret("desc", ret);
	ret = acpi_device_write_gpio(ctx, &gpio);
	if (ret < 0)
		return log_msg_ret("gpio", ret);

	return ret;
}

int acpi_device_write_interrupt_or_gpio(struct acpi_ctx *ctx,
					struct udevice *dev, const char *prop)
{
	struct irq req_irq;
	int pin;
	int ret;

	ret = irq_get_by_index(dev, 0, &req_irq);
	if (!ret) {
		ret = acpi_device_write_interrupt_irq(ctx, &req_irq);
		if (ret < 0)
			return log_msg_ret("irq", ret);
		pin = ret;
	} else {
		struct gpio_desc req_gpio;

		ret = gpio_request_by_name(dev, prop, 0, &req_gpio,
					   GPIOD_IS_IN);
		if (ret)
			return log_msg_ret("no gpio", ret);
		ret = acpi_device_write_gpio_desc(ctx, &req_gpio);
		if (ret < 0)
			return log_msg_ret("gpio", ret);
		pin = ret;
	}

	return pin;
}

/* PowerResource() with Enable and/or Reset control */
int acpi_device_add_power_res(struct acpi_ctx *ctx, u32 tx_state_val,
			      const char *dw0_read, const char *dw0_write,
			      const struct gpio_desc *reset_gpio,
			      uint reset_delay_ms, uint reset_off_delay_ms,
			      const struct gpio_desc *enable_gpio,
			      uint enable_delay_ms, uint enable_off_delay_ms,
			      const struct gpio_desc *stop_gpio,
			      uint stop_delay_ms, uint stop_off_delay_ms)
{
	static const char *const power_res_dev_states[] = { "_PR0", "_PR3" };
	struct acpi_gpio reset, enable, stop;
	bool has_reset, has_enable, has_stop;
	int ret;

	gpio_get_acpi(reset_gpio, &reset);
	gpio_get_acpi(enable_gpio, &enable);
	gpio_get_acpi(stop_gpio, &stop);
	has_reset = reset.pins[0];
	has_enable = enable.pins[0];
	has_stop = stop.pins[0];

	if (!has_reset && !has_enable && !has_stop)
		return -EINVAL;

	/* PowerResource (PRIC, 0, 0) */
	acpigen_write_power_res(ctx, "PRIC", 0, 0, power_res_dev_states,
				ARRAY_SIZE(power_res_dev_states));

	/* Method (_STA, 0, NotSerialized) { Return (0x1) } */
	acpigen_write_sta(ctx, 0x1);

	/* Method (_ON, 0, Serialized) */
	acpigen_write_method_serialized(ctx, "_ON", 0);
	if (reset_gpio) {
		ret = acpigen_set_enable_tx_gpio(ctx, tx_state_val, dw0_read,
						 dw0_write, &reset, true);
		if (ret)
			return log_msg_ret("reset1", ret);
	}
	if (has_enable) {
		ret = acpigen_set_enable_tx_gpio(ctx, tx_state_val, dw0_read,
						 dw0_write, &enable, true);
		if (ret)
			return log_msg_ret("enable1", ret);
		if (enable_delay_ms)
			acpigen_write_sleep(ctx, enable_delay_ms);
	}
	if (has_reset) {
		ret = acpigen_set_enable_tx_gpio(ctx, tx_state_val, dw0_read,
						 dw0_write, &reset, false);
		if (ret)
			return log_msg_ret("reset2", ret);
		if (reset_delay_ms)
			acpigen_write_sleep(ctx, reset_delay_ms);
	}
	if (has_stop) {
		ret = acpigen_set_enable_tx_gpio(ctx, tx_state_val, dw0_read,
						 dw0_write, &stop, false);
		if (ret)
			return log_msg_ret("stop1", ret);
		if (stop_delay_ms)
			acpigen_write_sleep(ctx, stop_delay_ms);
	}
	acpigen_pop_len(ctx);		/* _ON method */

	/* Method (_OFF, 0, Serialized) */
	acpigen_write_method_serialized(ctx, "_OFF", 0);
	if (has_stop) {
		ret = acpigen_set_enable_tx_gpio(ctx, tx_state_val, dw0_read,
						 dw0_write, &stop, true);
		if (ret)
			return log_msg_ret("stop2", ret);
		if (stop_off_delay_ms)
			acpigen_write_sleep(ctx, stop_off_delay_ms);
	}
	if (has_reset) {
		ret = acpigen_set_enable_tx_gpio(ctx, tx_state_val, dw0_read,
						 dw0_write, &reset, true);
		if (ret)
			return log_msg_ret("reset3", ret);
		if (reset_off_delay_ms)
			acpigen_write_sleep(ctx, reset_off_delay_ms);
	}
	if (has_enable) {
		ret = acpigen_set_enable_tx_gpio(ctx, tx_state_val, dw0_read,
						 dw0_write, &enable, false);
		if (ret)
			return log_msg_ret("enable2", ret);
		if (enable_off_delay_ms)
			acpigen_write_sleep(ctx, enable_off_delay_ms);
	}
	acpigen_pop_len(ctx);		/* _OFF method */

	acpigen_pop_len(ctx);		/* PowerResource PRIC */

	return 0;
}

int acpi_device_write_dsm_i2c_hid(struct acpi_ctx *ctx,
				  int hid_desc_reg_offset)
{
	int ret;

	acpigen_write_dsm_start(ctx);
	ret = acpigen_write_dsm_uuid_start(ctx, ACPI_DSM_I2C_HID_UUID);
	if (ret)
		return log_ret(ret);

	acpigen_write_dsm_uuid_start_cond(ctx, 0);
	/* ToInteger (Arg1, Local2) */
	acpigen_write_to_integer(ctx, ARG1_OP, LOCAL2_OP);
	/* If (LEqual (Local2, 0x0)) */
	acpigen_write_if_lequal_op_int(ctx, LOCAL2_OP, 0x0);
	/*   Return (Buffer (One) { 0x1f }) */
	acpigen_write_return_singleton_buffer(ctx, 0x1f);
	acpigen_pop_len(ctx);	/* Pop : If */
	/* Else */
	acpigen_write_else(ctx);
	/*   If (LEqual (Local2, 0x1)) */
	acpigen_write_if_lequal_op_int(ctx, LOCAL2_OP, 0x1);
	/*     Return (Buffer (One) { 0x3f }) */
	acpigen_write_return_singleton_buffer(ctx, 0x3f);
	acpigen_pop_len(ctx);	/* Pop : If */
	/*   Else */
	acpigen_write_else(ctx);
	/*     Return (Buffer (One) { 0x0 }) */
	acpigen_write_return_singleton_buffer(ctx, 0x0);
	acpigen_pop_len(ctx);	/* Pop : Else */
	acpigen_pop_len(ctx);	/* Pop : Else */
	acpigen_write_dsm_uuid_end_cond(ctx);

	acpigen_write_dsm_uuid_start_cond(ctx, 1);
	acpigen_write_return_byte(ctx, hid_desc_reg_offset);
	acpigen_write_dsm_uuid_end_cond(ctx);

	acpigen_write_dsm_uuid_end(ctx);
	acpigen_write_dsm_end(ctx);

	return 0;
}

/* ACPI 6.3 section 6.4.3.8.2.1 - I2cSerialBus() */
static void acpi_device_write_i2c(struct acpi_ctx *ctx,
				  const struct acpi_i2c *i2c)
{
	void *desc_length, *type_length;

	/* Byte 0: Descriptor Type */
	acpigen_emit_byte(ctx, ACPI_DESCRIPTOR_SERIAL_BUS);

	/* Byte 1+2: Length (filled in later) */
	desc_length = largeres_write_len_f(ctx);

	/* Byte 3: Revision ID */
	acpigen_emit_byte(ctx, ACPI_I2C_SERIAL_BUS_REVISION_ID);

	/* Byte 4: Resource Source Index is Reserved */
	acpigen_emit_byte(ctx, 0);

	/* Byte 5: Serial Bus Type is I2C */
	acpigen_emit_byte(ctx, ACPI_SERIAL_BUS_TYPE_I2C);

	/*
	 * Byte 6: Flags
	 *  [7:2]: 0 => Reserved
	 *    [1]: 1 => ResourceConsumer
	 *    [0]: 0 => ControllerInitiated
	 */
	acpigen_emit_byte(ctx, 1 << 1);

	/*
	 * Byte 7-8: Type Specific Flags
	 *   [15:1]: 0 => Reserved
	 *      [0]: 0 => 7bit, 1 => 10bit
	 */
	acpigen_emit_word(ctx, i2c->mode_10bit);

	/* Byte 9: Type Specific Revision ID */
	acpigen_emit_byte(ctx, ACPI_I2C_TYPE_SPECIFIC_REVISION_ID);

	/* Byte 10-11: I2C Type Data Length */
	type_length = largeres_write_len_f(ctx);

	/* Byte 12-15: I2C Bus Speed */
	acpigen_emit_dword(ctx, i2c->speed);

	/* Byte 16-17: I2C Slave Address */
	acpigen_emit_word(ctx, i2c->address);

	/* Fill in Type Data Length */
	largeres_fill_len(ctx, type_length);

	/* Byte 18+: ResourceSource */
	acpigen_emit_string(ctx, i2c->resource);

	/* Fill in I2C Descriptor Length */
	largeres_fill_len(ctx, desc_length);
}

/**
 * acpi_device_set_i2c() - Set up an ACPI I2C struct from a device
 *
 * The value of @scope is not copied, but only referenced. This implies the
 * caller has to ensure it stays valid for the lifetime of @i2c.
 *
 * @dev: I2C device to convert
 * @i2c: Place to put the new structure
 * @scope: Scope of the I2C device (this is the controller path)
 * @return chip address of device
 */
static int acpi_device_set_i2c(const struct udevice *dev, struct acpi_i2c *i2c,
			       const char *scope)
{
	struct dm_i2c_chip *chip = dev_get_parent_platdata(dev);
	struct udevice *bus = dev_get_parent(dev);

	memset(i2c, '\0', sizeof(*i2c));
	i2c->address = chip->chip_addr;
	i2c->mode_10bit = 0;

	/*
	 * i2c_bus->speed_hz is set if this device is probed, but if not we
	 * must use the device tree
	 */
	i2c->speed = dev_read_u32_default(bus, "clock-frequency",
					  I2C_SPEED_STANDARD_RATE);
	i2c->resource = scope;

	return i2c->address;
}

int acpi_device_write_i2c_dev(struct acpi_ctx *ctx, const struct udevice *dev)
{
	char scope[ACPI_PATH_MAX];
	struct acpi_i2c i2c;
	int ret;

	ret = acpi_device_scope(dev, scope, sizeof(scope));
	if (ret)
		return log_msg_ret("scope", ret);
	ret = acpi_device_set_i2c(dev, &i2c, scope);
	if (ret < 0)
		return log_msg_ret("set", ret);
	acpi_device_write_i2c(ctx, &i2c);

	return ret;
}

#ifdef CONFIG_SPI
/* ACPI 6.1 section 6.4.3.8.2.2 - SpiSerialBus() */
static void acpi_device_write_spi(struct acpi_ctx *ctx, const struct acpi_spi *spi)
{
	void *desc_length, *type_length;
	u16 flags = 0;

	/* Byte 0: Descriptor Type */
	acpigen_emit_byte(ctx, ACPI_DESCRIPTOR_SERIAL_BUS);

	/* Byte 1+2: Length (filled in later) */
	desc_length = largeres_write_len_f(ctx);

	/* Byte 3: Revision ID */
	acpigen_emit_byte(ctx, ACPI_SPI_SERIAL_BUS_REVISION_ID);

	/* Byte 4: Resource Source Index is Reserved */
	acpigen_emit_byte(ctx, 0);

	/* Byte 5: Serial Bus Type is SPI */
	acpigen_emit_byte(ctx, ACPI_SERIAL_BUS_TYPE_SPI);

	/*
	 * Byte 6: Flags
	 *  [7:2]: 0 => Reserved
	 *    [1]: 1 => ResourceConsumer
	 *    [0]: 0 => ControllerInitiated
	 */
	acpigen_emit_byte(ctx, BIT(1));

	/*
	 * Byte 7-8: Type Specific Flags
	 *   [15:2]: 0 => Reserveda
	 *      [1]: 0 => ActiveLow, 1 => ActiveHigh
	 *      [0]: 0 => FourWire, 1 => ThreeWire
	 */
	if (spi->wire_mode == SPI_3_WIRE_MODE)
		flags |= BIT(0);
	if (spi->device_select_polarity == SPI_POLARITY_HIGH)
		flags |= BIT(1);
	acpigen_emit_word(ctx, flags);

	/* Byte 9: Type Specific Revision ID */
	acpigen_emit_byte(ctx, ACPI_SPI_TYPE_SPECIFIC_REVISION_ID);

	/* Byte 10-11: SPI Type Data Length */
	type_length = largeres_write_len_f(ctx);

	/* Byte 12-15: Connection Speed */
	acpigen_emit_dword(ctx, spi->speed);

	/* Byte 16: Data Bit Length */
	acpigen_emit_byte(ctx, spi->data_bit_length);

	/* Byte 17: Clock Phase */
	acpigen_emit_byte(ctx, spi->clock_phase);

	/* Byte 18: Clock Polarity */
	acpigen_emit_byte(ctx, spi->clock_polarity);

	/* Byte 19-20: Device Selection */
	acpigen_emit_word(ctx, spi->device_select);

	/* Fill in Type Data Length */
	largeres_fill_len(ctx, type_length);

	/* Byte 21+: ResourceSource String */
	acpigen_emit_string(ctx, spi->resource);

	/* Fill in SPI Descriptor Length */
	largeres_fill_len(ctx, desc_length);
}

/**
 * acpi_device_set_spi() - Set up an ACPI SPI struct from a device
 *
 * The value of @scope is not copied, but only referenced. This implies the
 * caller has to ensure it stays valid for the lifetime of @spi.
 *
 * @dev: SPI device to convert
 * @spi: Place to put the new structure
 * @scope: Scope of the SPI device (this is the controller path)
 * @return 0 (always)
 */
static int acpi_device_set_spi(const struct udevice *dev, struct acpi_spi *spi,
			       const char *scope)
{
	struct dm_spi_slave_platdata *plat;
	struct spi_slave *slave = dev_get_parent_priv(dev);

	plat = dev_get_parent_platdata(slave->dev);
	memset(spi, '\0', sizeof(*spi));
	spi->device_select = plat->cs;
	spi->device_select_polarity = SPI_POLARITY_LOW;
	spi->wire_mode = SPI_4_WIRE_MODE;
	spi->speed = plat->max_hz;
	spi->data_bit_length = slave->wordlen;
	spi->clock_phase = plat->mode & SPI_CPHA ?
		 SPI_CLOCK_PHASE_SECOND : SPI_CLOCK_PHASE_FIRST;
	spi->clock_polarity = plat->mode & SPI_CPOL ?
		 SPI_POLARITY_HIGH : SPI_POLARITY_LOW;
	spi->resource = scope;

	return 0;
}

int acpi_device_write_spi_dev(struct acpi_ctx *ctx, const struct udevice *dev)
{
	char scope[ACPI_PATH_MAX];
	struct acpi_spi spi;
	int ret;

	ret = acpi_device_scope(dev, scope, sizeof(scope));
	if (ret)
		return log_msg_ret("scope", ret);
	ret = acpi_device_set_spi(dev, &spi, scope);
	if (ret)
		return log_msg_ret("set", ret);
	acpi_device_write_spi(ctx, &spi);

	return 0;
}
#endif /* CONFIG_SPI */

static const char *acpi_name_from_id(enum uclass_id id)
{
	switch (id) {
	case UCLASS_USB_HUB:
		/* Root Hub */
		return "RHUB";
	/* DSDT: acpi/northbridge.asl */
	case UCLASS_NORTHBRIDGE:
		return "MCHC";
	/* DSDT: acpi/lpc.asl */
	case UCLASS_LPC:
		return "LPCB";
	/* DSDT: acpi/xhci.asl */
	case UCLASS_USB:
		/* This only supports USB3.0 controllers at present */
		return "XHCI";
	case UCLASS_PWM:
		return "PWM";
	default:
		return NULL;
	}
}

static int acpi_check_seq(const struct udevice *dev)
{
	if (dev->req_seq == -1) {
		log_warning("Device '%s' has no seq\n", dev->name);
		return log_msg_ret("no seq", -ENXIO);
	}

	return dev->req_seq;
}

/* If you change this function, add test cases to dm_test_acpi_get_name() */
int acpi_device_infer_name(const struct udevice *dev, char *out_name)
{
	enum uclass_id parent_id = UCLASS_INVALID;
	enum uclass_id id;
	const char *name = NULL;

	id = device_get_uclass_id(dev);
	if (dev_get_parent(dev))
		parent_id = device_get_uclass_id(dev_get_parent(dev));

	if (id == UCLASS_SOUND)
		name = "HDAS";
	else if (id == UCLASS_PCI)
		name = "PCI0";
	else if (device_is_on_pci_bus(dev))
		name = acpi_name_from_id(id);
	if (!name) {
		switch (parent_id) {
		case UCLASS_USB: {
			struct usb_device *udev = dev_get_parent_priv(dev);

			sprintf(out_name, udev->speed >= USB_SPEED_SUPER ?
				"HS%02d" : "FS%02d", udev->portnr);
			name = out_name;
			break;
		}
		default:
			break;
		}
	}
	if (!name) {
		int num;

		switch (id) {
		/* DSDT: acpi/lpss.asl */
		case UCLASS_SERIAL:
			num = acpi_check_seq(dev);
			if (num < 0)
				return num;
			sprintf(out_name, "URT%d", num);
			name = out_name;
			break;
		case UCLASS_I2C:
			num = acpi_check_seq(dev);
			if (num < 0)
				return num;
			sprintf(out_name, "I2C%d", num);
			name = out_name;
			break;
		case UCLASS_SPI:
			num = acpi_check_seq(dev);
			if (num < 0)
				return num;
			sprintf(out_name, "SPI%d", num);
			name = out_name;
			break;
		default:
			break;
		}
	}
	if (!name) {
		log_warning("No name for device '%s'\n", dev->name);
		return -ENOENT;
	}
	if (name != out_name)
		acpi_copy_name(out_name, name);

	return 0;
}
