@@ -4,6 +4,7 @@
*/
#include <common.h>
+#include <acpi_device.h>
#include <dm.h>
#include <dm/device-internal.h>
#include <dm/lists.h>
@@ -697,6 +698,26 @@ int gpio_get_status(struct udevice *dev, int offset, char *buf, int buffsize)
return 0;
}
+#if CONFIG_IS_ENABLED(ACPIGEN)
+int gpio_get_acpi(const struct gpio_desc *desc, struct acpi_gpio *gpio)
+{
+ struct dm_gpio_ops *ops;
+
+ if (!dm_gpio_is_valid(desc)) {
+ /* Indicate that the GPIO is not valid */
+ gpio->pin_count = 0;
+ gpio->pins[0] = 0;
+ return -EINVAL;
+ }
+
+ ops = gpio_get_ops(desc->dev);
+ if (!ops->get_acpi)
+ return -ENOSYS;
+
+ return ops->get_acpi(desc, gpio);
+}
+#endif
+
int gpio_claim_vector(const int *gpio_num_array, const char *fmt)
{
int i, ret;
@@ -533,6 +533,18 @@ size_t acpi_dp_add_property_list(struct acpi_dp *dp,
*/
int acpi_dp_write(struct acpi_ctx *ctx, struct acpi_dp *table);
+/**
+ * acpi_device_write_gpio_desc() - Write a GPIO to ACPI
+ *
+ * This creates a GPIO descriptor for a GPIO, including information ACPI needs
+ * to use it. The type is always ACPI_GPIO_TYPE_IO.
+ *
+ * @desc: GPIO to write
+ * @return 0 if OK, -ve on error
+ */
+int acpi_device_write_gpio_desc(struct acpi_ctx *ctx,
+ const struct gpio_desc *desc);
+
/**
* acpi_device_write_i2c_dev() - Write an I2C device to ACPI, including
* information ACPI needs to use it.
@@ -9,6 +9,7 @@
#include <dm/ofnode.h>
+struct acpi_gpio;
struct ofnode_phandle_args;
/*
@@ -290,6 +291,20 @@ struct dm_gpio_ops {
*/
int (*xlate)(struct udevice *dev, struct gpio_desc *desc,
struct ofnode_phandle_args *args);
+
+#if CONFIG_IS_ENABLED(ACPIGEN)
+ /**
+ * get_acpi() - Get the ACPI info for a GPIO
+ *
+ * This converts a GPIO to an ACPI structure for adding to the ACPI
+ * tables.
+ *
+ * @desc: GPIO description to convert
+ * @gpio: Output ACPI GPIO information
+ * @return ACPI pin number or -ve on error
+ */
+ int (*get_acpi)(const struct gpio_desc *desc, struct acpi_gpio *gpio);
+#endif
};
/**
@@ -657,4 +672,16 @@ int dm_gpio_set_dir_flags(struct gpio_desc *desc, ulong flags);
*/
int gpio_get_number(const struct gpio_desc *desc);
+/**
+ * gpio_get_acpi() - Get the ACPI pin for a GPIO
+ *
+ * This converts a GPIO to an ACPI pin number for adding to the ACPI
+ * tables. If the GPIO is invalid, the pin_count and pins[0] are set to 0
+ *
+ * @desc: GPIO description to convert
+ * @gpio: Output ACPI GPIO information
+ * @return ACPI pin number or -ve on error
+ */
+int gpio_get_acpi(const struct gpio_desc *desc, struct acpi_gpio *gpio);
+
#endif /* _ASM_GENERIC_GPIO_H_ */
@@ -287,6 +287,22 @@ int acpi_device_write_gpio(struct acpi_ctx *ctx, const struct acpi_gpio *gpio)
return 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)
+ return log_msg_ret("gpio", ret);
+
+ return 0;
+}
+
/* ACPI 6.1 section 6.4.3.8.2.1 - I2cSerialBus() */
static void acpi_device_write_i2c(struct acpi_ctx *ctx,
const struct acpi_i2c *i2c)
When generating ACPI tables we need to convert GPIOs in U-Boot to the ACPI structures required by ACPI. This is a SoC-specific conversion and cannot be handled by generic code, so add a new GPIO method to do the conversion. Signed-off-by: Simon Glass <sjg at chromium.org> --- drivers/gpio/gpio-uclass.c | 21 +++++++++++++++++++++ include/acpi_device.h | 12 ++++++++++++ include/asm-generic/gpio.h | 27 +++++++++++++++++++++++++++ lib/acpi/acpi_device.c | 16 ++++++++++++++++ 4 files changed, 76 insertions(+)