acpi: Move ACPI table support out of arch/x86 (2/5)
This change moves all ACPI table support in coreboot currently living under arch/x86 into common code to make it architecture independent. ACPI table generation is not really tied to any architecture and hence it makes sense to move this to its own directory. In order to make it easier to review, this change is being split into multiple CLs. This is change 2/5 which moves the contents of arch/x86/include/arch/acpi*.h files into include/acpi/acpi*.h and updates the arch header files to include acpi header files. These are just temporary placeholders and will be removed later in the series. BUG=b:155428745 Change-Id: I9acb787770b7f09fd2cbd99cb8d0a6499b9c64b3 Signed-off-by: Furquan Shaikh <furquan@google.com> Reviewed-on: https://review.coreboot.org/c/coreboot/+/40937 Tested-by: build bot (Jenkins) <no-reply@coreboot.org> Reviewed-by: HAOUAS Elyes <ehaouas@noos.fr>
This commit is contained in:
parent
6cc1e9e81e
commit
e0844636ac
File diff suppressed because it is too large
Load Diff
|
@ -1,513 +1,4 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
#ifndef __ACPI_DEVICE_H
|
||||
#define __ACPI_DEVICE_H
|
||||
|
||||
#include <device/i2c.h>
|
||||
#include <stdint.h>
|
||||
#include <spi-generic.h>
|
||||
|
||||
enum acpi_dp_type {
|
||||
ACPI_DP_TYPE_UNKNOWN,
|
||||
ACPI_DP_TYPE_INTEGER,
|
||||
ACPI_DP_TYPE_STRING,
|
||||
ACPI_DP_TYPE_REFERENCE,
|
||||
ACPI_DP_TYPE_TABLE,
|
||||
ACPI_DP_TYPE_ARRAY,
|
||||
ACPI_DP_TYPE_CHILD,
|
||||
};
|
||||
|
||||
struct acpi_dp {
|
||||
enum acpi_dp_type type;
|
||||
const char *name;
|
||||
struct acpi_dp *next;
|
||||
union {
|
||||
struct acpi_dp *child;
|
||||
struct acpi_dp *array;
|
||||
};
|
||||
union {
|
||||
uint64_t integer;
|
||||
const char *string;
|
||||
};
|
||||
};
|
||||
|
||||
#define ACPI_DESCRIPTOR_LARGE (1 << 7)
|
||||
#define ACPI_DESCRIPTOR_INTERRUPT (ACPI_DESCRIPTOR_LARGE | 9)
|
||||
#define ACPI_DESCRIPTOR_GPIO (ACPI_DESCRIPTOR_LARGE | 12)
|
||||
#define ACPI_DESCRIPTOR_SERIAL_BUS (ACPI_DESCRIPTOR_LARGE | 14)
|
||||
|
||||
/*
|
||||
* PRP0001 is a special DT namespace link device ID. It provides a means to use
|
||||
* existing DT-compatible device identification in ACPI. When this _HID is used
|
||||
* by an ACPI device, the ACPI subsystem in OS looks up "compatible" property in
|
||||
* device object's _DSD and will use the value of that property to identify the
|
||||
* corresponding device in analogy with the original DT device identification
|
||||
* algorithm.
|
||||
* More details can be found in Linux kernel documentation:
|
||||
* Documentation/acpi/enumeration.txt
|
||||
*/
|
||||
#define ACPI_DT_NAMESPACE_HID "PRP0001"
|
||||
|
||||
struct device;
|
||||
const char *acpi_device_name(const struct device *dev);
|
||||
const char *acpi_device_hid(const struct device *dev);
|
||||
uint32_t acpi_device_uid(const struct device *dev);
|
||||
const char *acpi_device_path(const struct device *dev);
|
||||
const char *acpi_device_scope(const struct device *dev);
|
||||
const char *acpi_device_path_join(const struct device *dev, const char *name);
|
||||
int acpi_device_status(const struct device *dev);
|
||||
void acpi_device_write_uid(const struct device *dev);
|
||||
|
||||
/*
|
||||
* ACPI Descriptor for extended Interrupt()
|
||||
*/
|
||||
|
||||
enum acpi_irq_mode {
|
||||
ACPI_IRQ_EDGE_TRIGGERED,
|
||||
ACPI_IRQ_LEVEL_TRIGGERED
|
||||
};
|
||||
|
||||
enum acpi_irq_polarity {
|
||||
ACPI_IRQ_ACTIVE_LOW,
|
||||
ACPI_IRQ_ACTIVE_HIGH,
|
||||
ACPI_IRQ_ACTIVE_BOTH
|
||||
};
|
||||
|
||||
enum acpi_irq_shared {
|
||||
ACPI_IRQ_EXCLUSIVE,
|
||||
ACPI_IRQ_SHARED
|
||||
};
|
||||
|
||||
enum acpi_irq_wake {
|
||||
ACPI_IRQ_NO_WAKE,
|
||||
ACPI_IRQ_WAKE
|
||||
};
|
||||
|
||||
struct acpi_irq {
|
||||
unsigned int pin;
|
||||
enum acpi_irq_mode mode;
|
||||
enum acpi_irq_polarity polarity;
|
||||
enum acpi_irq_shared shared;
|
||||
enum acpi_irq_wake wake;
|
||||
};
|
||||
|
||||
#define ACPI_IRQ_CFG(_pin, _mode, _pol, _shared, _wake) { \
|
||||
.pin = (_pin), \
|
||||
.mode = (_mode), \
|
||||
.polarity = (_pol), \
|
||||
.shared = (_shared), \
|
||||
.wake = (_wake) }
|
||||
|
||||
#define ACPI_IRQ_EDGE_LOW(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_EDGE_TRIGGERED, ACPI_IRQ_ACTIVE_LOW, \
|
||||
ACPI_IRQ_EXCLUSIVE, ACPI_IRQ_NO_WAKE)
|
||||
|
||||
#define ACPI_IRQ_EDGE_HIGH(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_EDGE_TRIGGERED, ACPI_IRQ_ACTIVE_HIGH, \
|
||||
ACPI_IRQ_EXCLUSIVE, ACPI_IRQ_NO_WAKE)
|
||||
|
||||
#define ACPI_IRQ_LEVEL_LOW(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_LEVEL_TRIGGERED, ACPI_IRQ_ACTIVE_LOW, \
|
||||
ACPI_IRQ_SHARED, ACPI_IRQ_NO_WAKE)
|
||||
|
||||
#define ACPI_IRQ_LEVEL_HIGH(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_LEVEL_TRIGGERED, ACPI_IRQ_ACTIVE_HIGH, \
|
||||
ACPI_IRQ_SHARED, ACPI_IRQ_NO_WAKE)
|
||||
|
||||
#define ACPI_IRQ_WAKE_EDGE_LOW(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_EDGE_TRIGGERED, ACPI_IRQ_ACTIVE_LOW, \
|
||||
ACPI_IRQ_EXCLUSIVE, ACPI_IRQ_WAKE)
|
||||
|
||||
#define ACPI_IRQ_WAKE_EDGE_HIGH(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_EDGE_TRIGGERED, ACPI_IRQ_ACTIVE_HIGH, \
|
||||
ACPI_IRQ_EXCLUSIVE, ACPI_IRQ_WAKE)
|
||||
|
||||
#define ACPI_IRQ_WAKE_LEVEL_LOW(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_LEVEL_TRIGGERED, ACPI_IRQ_ACTIVE_LOW, \
|
||||
ACPI_IRQ_SHARED, ACPI_IRQ_WAKE)
|
||||
|
||||
#define ACPI_IRQ_WAKE_LEVEL_HIGH(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_LEVEL_TRIGGERED, ACPI_IRQ_ACTIVE_HIGH, \
|
||||
ACPI_IRQ_SHARED, ACPI_IRQ_WAKE)
|
||||
|
||||
/* Write extended Interrupt() descriptor to SSDT AML output */
|
||||
void acpi_device_write_interrupt(const struct acpi_irq *irq);
|
||||
|
||||
/*
|
||||
* ACPI Descriptors for GpioIo() and GpioInterrupt()
|
||||
*/
|
||||
|
||||
enum acpi_gpio_type {
|
||||
ACPI_GPIO_TYPE_INTERRUPT,
|
||||
ACPI_GPIO_TYPE_IO
|
||||
};
|
||||
|
||||
enum acpi_gpio_pull {
|
||||
ACPI_GPIO_PULL_DEFAULT,
|
||||
ACPI_GPIO_PULL_UP,
|
||||
ACPI_GPIO_PULL_DOWN,
|
||||
ACPI_GPIO_PULL_NONE
|
||||
};
|
||||
|
||||
enum acpi_gpio_io_restrict {
|
||||
ACPI_GPIO_IO_RESTRICT_NONE,
|
||||
ACPI_GPIO_IO_RESTRICT_INPUT,
|
||||
ACPI_GPIO_IO_RESTRICT_OUTPUT,
|
||||
ACPI_GPIO_IO_RESTRICT_PRESERVE
|
||||
};
|
||||
|
||||
enum acpi_gpio_polarity {
|
||||
ACPI_GPIO_ACTIVE_HIGH = 0,
|
||||
ACPI_GPIO_ACTIVE_LOW = 1,
|
||||
};
|
||||
|
||||
#define ACPI_GPIO_REVISION_ID 1
|
||||
#define ACPI_GPIO_MAX_PINS 8
|
||||
|
||||
struct acpi_gpio {
|
||||
int pin_count;
|
||||
uint16_t pins[ACPI_GPIO_MAX_PINS];
|
||||
|
||||
enum acpi_gpio_type type;
|
||||
enum acpi_gpio_pull pull;
|
||||
const char *resource;
|
||||
|
||||
/* GpioInt */
|
||||
uint16_t interrupt_debounce_timeout; /* 1/100 ms */
|
||||
struct acpi_irq irq;
|
||||
|
||||
/* GpioIo */
|
||||
uint16_t output_drive_strength; /* 1/100 mA */
|
||||
int io_shared;
|
||||
enum acpi_gpio_io_restrict io_restrict;
|
||||
enum acpi_gpio_polarity polarity;
|
||||
};
|
||||
|
||||
/* Basic output GPIO with default pull settings */
|
||||
#define ACPI_GPIO_OUTPUT_ACTIVE_HIGH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_IO, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.io_restrict = ACPI_GPIO_IO_RESTRICT_OUTPUT, \
|
||||
.polarity = ACPI_GPIO_ACTIVE_HIGH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
#define ACPI_GPIO_OUTPUT_ACTIVE_LOW(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_IO, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.io_restrict = ACPI_GPIO_IO_RESTRICT_OUTPUT, \
|
||||
.polarity = ACPI_GPIO_ACTIVE_LOW, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Basic input GPIO with default pull settings */
|
||||
#define ACPI_GPIO_INPUT_ACTIVE_HIGH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_IO, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.io_restrict = ACPI_GPIO_IO_RESTRICT_INPUT, \
|
||||
.polarity = ACPI_GPIO_ACTIVE_HIGH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
#define ACPI_GPIO_INPUT_ACTIVE_LOW(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_IO, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.io_restrict = ACPI_GPIO_IO_RESTRICT_INPUT, \
|
||||
.polarity = ACPI_GPIO_ACTIVE_LOW, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active High GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_EDGE_HIGH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_HIGH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active Low GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_EDGE_LOW(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_LOW, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active Both GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_EDGE_BOTH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_BOTH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active High GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_EDGE_HIGH_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_HIGH, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active Low GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_EDGE_LOW_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_LOW, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active Both GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_EDGE_BOTH_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_BOTH, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Level Triggered Active High GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_LEVEL_HIGH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_LEVEL_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_HIGH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Level Triggered Active Low GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_LEVEL_LOW(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_LEVEL_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_LOW, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Level Triggered Active High GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_LEVEL_HIGH_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_LEVEL_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_HIGH, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Level Triggered Active Low GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_LEVEL_LOW_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_LEVEL_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_LOW, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Write GpioIo() or GpioInt() descriptor to SSDT AML output */
|
||||
void acpi_device_write_gpio(const struct acpi_gpio *gpio);
|
||||
|
||||
/*
|
||||
* ACPI Descriptors for Serial Bus interfaces
|
||||
*/
|
||||
|
||||
#define ACPI_SERIAL_BUS_TYPE_I2C 1
|
||||
#define ACPI_SERIAL_BUS_TYPE_SPI 2
|
||||
#define ACPI_I2C_SERIAL_BUS_REVISION_ID 1 /* TODO: upgrade to 2 */
|
||||
#define ACPI_I2C_TYPE_SPECIFIC_REVISION_ID 1
|
||||
#define ACPI_SPI_SERIAL_BUS_REVISION_ID 1
|
||||
#define ACPI_SPI_TYPE_SPECIFIC_REVISION_ID 1
|
||||
|
||||
/*
|
||||
* ACPI I2C Bus
|
||||
*/
|
||||
|
||||
struct acpi_i2c {
|
||||
/* I2C Address */
|
||||
uint16_t address;
|
||||
/* 7 or 10 bit Address Mode */
|
||||
enum i2c_address_mode mode_10bit;
|
||||
/* I2C Bus Speed in Hz */
|
||||
enum i2c_speed speed;
|
||||
/* Reference to I2C controller */
|
||||
const char *resource;
|
||||
};
|
||||
|
||||
/* Write I2cSerialBus() descriptor to SSDT AML output */
|
||||
void acpi_device_write_i2c(const struct acpi_i2c *i2c);
|
||||
|
||||
/*
|
||||
* ACPI SPI Bus
|
||||
*/
|
||||
|
||||
struct acpi_spi {
|
||||
/* Device selection */
|
||||
uint16_t device_select;
|
||||
/* Device selection line is active high or low */
|
||||
enum spi_polarity device_select_polarity;
|
||||
/* 3 or 4 wire SPI connection */
|
||||
enum spi_wire_mode wire_mode;
|
||||
/* Connection speed in HZ */
|
||||
unsigned int speed;
|
||||
/* Size in bits of smallest transfer unit */
|
||||
u8 data_bit_length;
|
||||
/* Phase of clock pulse on which to capture data */
|
||||
enum spi_clock_phase clock_phase;
|
||||
/* Indicate if clock is high or low during first phase */
|
||||
enum spi_polarity clock_polarity;
|
||||
/* Reference to SPI controller */
|
||||
const char *resource;
|
||||
};
|
||||
|
||||
/* Write SPI Bus descriptor to SSDT AML output */
|
||||
void acpi_device_write_spi(const struct acpi_spi *spi);
|
||||
|
||||
/* GPIO/timing information for the power on/off sequences */
|
||||
struct acpi_power_res_params {
|
||||
/* GPIO used to take device out of reset or to put it into reset. */
|
||||
struct acpi_gpio *reset_gpio;
|
||||
/* Delay to be inserted after device is taken out of reset.
|
||||
* (_ON method delay)
|
||||
*/
|
||||
unsigned int reset_delay_ms;
|
||||
/* Delay to be inserted after device is put into reset.
|
||||
* (_OFF method delay)
|
||||
*/
|
||||
unsigned int reset_off_delay_ms;
|
||||
/* GPIO used to enable device. */
|
||||
struct acpi_gpio *enable_gpio;
|
||||
/* Delay to be inserted after device is enabled.
|
||||
* (_ON method delay)
|
||||
*/
|
||||
unsigned int enable_delay_ms;
|
||||
/* Delay to be inserted after device is disabled.
|
||||
* (_OFF method delay)
|
||||
*/
|
||||
unsigned int enable_off_delay_ms;
|
||||
/* GPIO used to stop operation of device. */
|
||||
struct acpi_gpio *stop_gpio;
|
||||
/* Delay to be inserted after disabling stop.
|
||||
* (_ON method delay)
|
||||
*/
|
||||
unsigned int stop_delay_ms;
|
||||
/* Delay to be inserted after enabling stop.
|
||||
* (_OFF method delay)
|
||||
*/
|
||||
unsigned int stop_off_delay_ms;
|
||||
};
|
||||
|
||||
/*
|
||||
* Add a basic PowerResource block for a device that includes
|
||||
* GPIOs to control enable, reset and stop operation of the device. Each
|
||||
* GPIO is optional, but at least one must be provided.
|
||||
*
|
||||
* Reset - Put the device into / take the device out of reset.
|
||||
* Enable - Enable / disable power to device.
|
||||
* Stop - Stop / start operation of device.
|
||||
*/
|
||||
void acpi_device_add_power_res(const struct acpi_power_res_params *params);
|
||||
|
||||
/*
|
||||
* Writing Device Properties objects via _DSD
|
||||
*
|
||||
* http://uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
|
||||
* http://uefi.org/sites/default/files/resources/_DSD-hierarchical-data-extension-UUID-v1.pdf
|
||||
*
|
||||
* The Device Property Hierarchy can be multiple levels deep with multiple
|
||||
* children possible in each level. In order to support this flexibility
|
||||
* the device property hierarchy must be built up before being written out.
|
||||
*
|
||||
* For example:
|
||||
*
|
||||
* // Child table with string and integer
|
||||
* struct acpi_dp *child = acpi_dp_new_table("CHLD");
|
||||
* acpi_dp_add_string(child, "childstring", "CHILD");
|
||||
* acpi_dp_add_integer(child, "childint", 100);
|
||||
*
|
||||
* // _DSD table with integer and gpio and child pointer
|
||||
* struct acpi_dp *dsd = acpi_dp_new_table("_DSD");
|
||||
* acpi_dp_add_integer(dsd, "number1", 1);
|
||||
* acpi_dp_add_gpio(dsd, "gpio", "\_SB.PCI0.GPIO", 0, 0, 1);
|
||||
* acpi_dp_add_child(dsd, "child", child);
|
||||
*
|
||||
* // Write entries into SSDT and clean up resources
|
||||
* acpi_dp_write(dsd);
|
||||
*
|
||||
* Name(_DSD, Package() {
|
||||
* ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301")
|
||||
* Package() {
|
||||
* Package() { "gpio", Package() { \_SB.PCI0.GPIO, 0, 0, 0 } }
|
||||
* Package() { "number1", 1 }
|
||||
* }
|
||||
* ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b")
|
||||
* Package() {
|
||||
* Package() { "child", CHLD }
|
||||
* }
|
||||
* }
|
||||
* Name(CHLD, Package() {
|
||||
* ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301")
|
||||
* Package() {
|
||||
* Package() { "childstring", "CHILD" }
|
||||
* Package() { "childint", 100 }
|
||||
* }
|
||||
* }
|
||||
*/
|
||||
|
||||
/* Start a new Device Property table with provided ACPI reference */
|
||||
struct acpi_dp *acpi_dp_new_table(const char *ref);
|
||||
|
||||
/* Add integer Device Property */
|
||||
struct acpi_dp *acpi_dp_add_integer(struct acpi_dp *dp, const char *name,
|
||||
uint64_t value);
|
||||
|
||||
/* Add string Device Property */
|
||||
struct acpi_dp *acpi_dp_add_string(struct acpi_dp *dp, const char *name,
|
||||
const char *string);
|
||||
|
||||
/* Add ACPI reference Device Property */
|
||||
struct acpi_dp *acpi_dp_add_reference(struct acpi_dp *dp, const char *name,
|
||||
const char *reference);
|
||||
|
||||
/* Add an array of Device Properties */
|
||||
struct acpi_dp *acpi_dp_add_array(struct acpi_dp *dp, struct acpi_dp *array);
|
||||
|
||||
/* Add an array of integers Device Property */
|
||||
struct acpi_dp *acpi_dp_add_integer_array(struct acpi_dp *dp, const char *name,
|
||||
const uint64_t *array, int len);
|
||||
|
||||
/* Add a GPIO binding Device Property */
|
||||
struct acpi_dp *acpi_dp_add_gpio(struct acpi_dp *dp, const char *name,
|
||||
const char *ref, int index, int pin,
|
||||
int active_low);
|
||||
|
||||
/* Add a child table of Device Properties */
|
||||
struct acpi_dp *acpi_dp_add_child(struct acpi_dp *dp, const char *name,
|
||||
struct acpi_dp *child);
|
||||
|
||||
/* Add a list of Device Properties, returns the number of properties added */
|
||||
size_t acpi_dp_add_property_list(struct acpi_dp *dp,
|
||||
const struct acpi_dp *property_list,
|
||||
size_t property_count);
|
||||
|
||||
/* Write Device Property hierarchy and clean up resources */
|
||||
void acpi_dp_write(struct acpi_dp *table);
|
||||
|
||||
/*
|
||||
* Helper function to write a PCI device with _ADR object defined.
|
||||
*
|
||||
* IMPORTANT: Scope of a device created in SSDT cannot be used to add ACPI nodes under that
|
||||
* scope in DSDT. So, if there are any references to this PCI device scope required from static
|
||||
* asl files, do not use this function and instead add the device to DSDT as well.
|
||||
*/
|
||||
void acpi_device_write_pci_dev(const struct device *dev);
|
||||
|
||||
#endif
|
||||
#include <acpi/acpi_device.h>
|
||||
|
|
|
@ -1,143 +1,4 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
/*
|
||||
* AMD I/O Virtualization Technology (IOMMU)
|
||||
* Specification 48882-Rev 2.62-February 2015
|
||||
*
|
||||
* from http://www.uefi.org/acpi
|
||||
* I/O Virtualization Reporting Structure (IVRS)
|
||||
*/
|
||||
|
||||
#ifndef __ARCH_ACPI_IVRS_H
|
||||
#define __ARCH_ACPI_IVRS_H
|
||||
|
||||
/* I/O Virtualization Reporting Structure (IVRS) */
|
||||
#define IVHD_BLOCK_TYPE_LEGACY__FIXED 0x10
|
||||
#define IVHD_BLOCK_TYPE_FULL__FIXED 0x11
|
||||
#define IVHD_BLOCK_TYPE_FULL__ACPI_HID 0x40
|
||||
|
||||
/* IVRS Revision Field */
|
||||
#define IVRS_FORMAT_FIXED 0x01 /* Type 10h & 11h only */
|
||||
#define IVRS_FORMAT_MIXED 0x02 /* Type 10h, 11h, & 40h */
|
||||
|
||||
/* IVRS IVinfo Field */
|
||||
/* ATS response address range reserved */
|
||||
#define IVINFO_HT_ATS_RESERVED (1 << 22)
|
||||
|
||||
/* Virtual Address size - All other values are reserved */
|
||||
#define IVINFO_VA_SIZE_32_BITS (0x20 << 15)
|
||||
#define IVINFO_VA_SIZE_40_BITS (0x28 << 15)
|
||||
#define IVINFO_VA_SIZE_48_BITS (0x30 << 15)
|
||||
#define IVINFO_VA_SIZE_64_BITS (0x40 << 15)
|
||||
|
||||
/* Physical Address size - All other values are reserved */
|
||||
#define IVINFO_PA_SIZE_40_BITS (0x28 << 8)
|
||||
#define IVINFO_PA_SIZE_48_BITS (0x30 << 8)
|
||||
#define IVINFO_PA_SIZE_52_BITS (0x34 << 8)
|
||||
|
||||
/* Guest Virtual Address size - All other values are reserved */
|
||||
#define IVINFO_GVA_SIZE_48_BITS (0x02 << 5)
|
||||
|
||||
/* Extended Feature Support */
|
||||
#define IVINFO_EFR_SUPPORTED 0x01
|
||||
|
||||
/* IVHD Flags Field */
|
||||
#define IVHD_FLAG_PPE_SUP (1 << 7) /* Type 10h only */
|
||||
#define IVHD_FLAG_PREF_SUP (1 << 6) /* Type 10h only */
|
||||
#define IVHD_FLAG_COHERENT (1 << 5)
|
||||
#define IVHD_FLAG_IOTLB_SUP (1 << 4)
|
||||
#define IVHD_FLAG_ISOC (1 << 3)
|
||||
#define IVHD_FLAG_RES_PASS_PW (1 << 2)
|
||||
#define IVHD_FLAG_PASS_PW (1 << 1)
|
||||
#define IVHD_FLAG_HT_TUN_EN (1 << 0)
|
||||
|
||||
/* IVHD IOMMU Info Field */
|
||||
#define IOMMU_INFO_UNIT_ID_SHIFT 8
|
||||
|
||||
/* IVHD IOMMU Feature Reporting Field */
|
||||
#define IOMMU_FEATURE_HATS_SHIFT 30 /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GATS_SHIFT 28 /* Type 10h only */
|
||||
#define IOMMU_FEATURE_MSI_NUM_PPR_SHIFT 23
|
||||
#define IOMMU_FEATURE_PN_BANKS_SHIFT 17
|
||||
#define IOMMU_FEATURE_PN_COUNTERS_SHIFT 13
|
||||
#define IOMMU_FEATURE_PA_SMAX_SHIFT 8 /* Type 10h only */
|
||||
|
||||
#define IOMMU_FEATURE_HE_SUP (1 << 7) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GA_SUP (1 << 6) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_IA_SUP (1 << 5) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GLX_SINGLE_LEVEL (0 << 3) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GLX_TWO_LEVEL (1 << 3) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GLX_THREE_LEVEL (2 << 3) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GT_SUP (1 << 1) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_NX_SUP (1 << 0) /* Type 10h only */
|
||||
|
||||
/* IVHD Device Entry Type Codes */
|
||||
#define IVHD_DEV_4_BYTE_ALL 0x01
|
||||
#define IVHD_DEV_4_BYTE_SELECT 0x02
|
||||
#define IVHD_DEV_4_BYTE_START_RANGE 0x03
|
||||
#define IVHD_DEV_4_BYTE_END_RANGE 0x04
|
||||
#define IVHD_DEV_8_BYTE_ALIAS_SELECT 0x42
|
||||
#define IVHD_DEV_8_BYTE_ALIAS_START_RANGE 0x43
|
||||
#define IVHD_DEV_8_BYTE_EXT_SELECT 0x46
|
||||
#define IVHD_DEV_8_BYTE_EXT_START_RANGE 0x47
|
||||
#define IVHD_DEV_8_BYTE_EXT_SPECIAL_DEV 0x48
|
||||
#define IVHD_DEV_VARIABLE 0xF0
|
||||
|
||||
/* IVHD Device Table Entry (DTE) Settings */
|
||||
#define IVHD_DTE_LINT_1_PASS (1 << 7)
|
||||
#define IVHD_DTE_LINT_0_PASS (1 << 6)
|
||||
#define IVHD_DTE_SYS_MGT_TGT_ABT (0 << 4)
|
||||
#define IVHD_DTE_SYS_MGT_NO_TRANS (1 << 4)
|
||||
#define IVHD_DTE_SYS_MGT_INTX_NO_TRANS (2 << 4)
|
||||
#define IVHD_DTE_SYS_MGT_TRANS (3 << 4)
|
||||
#define IVHD_DTE_NMI_PASS (1 << 2)
|
||||
#define IVHD_DTE_EXT_INT_PASS (1 << 1)
|
||||
#define IVHD_DTE_INIT_PASS (1 << 0)
|
||||
|
||||
/* IVHD Device Entry Extended DTE Setting Field */
|
||||
#define IVHD_DEV_EXT_ATS_DISABLE (1 << 31)
|
||||
|
||||
/* IVHD Special Device Entry Variety Field */
|
||||
#define IVHD_SPECIAL_DEV_IOAPIC 0x01
|
||||
#define IVHD_SPECIAL_DEV_HPET 0x02
|
||||
|
||||
/* Device EntryType F0h UID Format */
|
||||
#define IVHD_UID_NOT_PRESENT 0x00
|
||||
#define IVHD_UID_INT 0x01
|
||||
#define IVHD_UID_STRING 0x02
|
||||
|
||||
/* IVHD (I/O Virtualization Hardware Definition Block) 4-byte entry */
|
||||
typedef struct ivrs_ivhd_generic {
|
||||
uint8_t type;
|
||||
uint16_t dev_id;
|
||||
uint8_t dte_setting;
|
||||
} __packed ivrs_ivhd_generic_t;
|
||||
|
||||
/* IVHD (I/O Virtualization Hardware Definition Block) 8-byte entries */
|
||||
typedef struct ivrs_ivhd_alias {
|
||||
uint8_t type;
|
||||
uint16_t dev_id;
|
||||
uint8_t dte_setting;
|
||||
uint8_t reserved1;
|
||||
uint16_t source_dev_id;
|
||||
uint8_t reserved2;
|
||||
} __packed ivrs_ivhd_alias_t;
|
||||
|
||||
typedef struct ivrs_ivhd_extended {
|
||||
uint8_t type;
|
||||
uint16_t dev_id;
|
||||
uint8_t dte_setting;
|
||||
uint32_t extended_dte_setting;
|
||||
} __packed ivrs_ivhd_extended_t;
|
||||
|
||||
typedef struct ivrs_ivhd_special {
|
||||
uint8_t type;
|
||||
uint16_t reserved;
|
||||
uint8_t dte_setting;
|
||||
uint8_t handle;
|
||||
uint16_t source_dev_id;
|
||||
uint8_t variety;
|
||||
} __packed ivrs_ivhd_special_t;
|
||||
|
||||
#endif
|
||||
#include <acpi/acpi_ivrs.h>
|
||||
|
|
|
@ -1,119 +1,4 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
#ifndef __ACPI_PLD_H
|
||||
#define __ACPI_PLD_H
|
||||
|
||||
#include <arch/acpi.h>
|
||||
#include <stdint.h>
|
||||
|
||||
enum acpi_pld_panel {
|
||||
PLD_PANEL_TOP,
|
||||
PLD_PANEL_BOTTOM,
|
||||
PLD_PANEL_LEFT,
|
||||
PLD_PANEL_RIGHT,
|
||||
PLD_PANEL_FRONT,
|
||||
PLD_PANEL_BACK,
|
||||
PLD_PANEL_UNKNOWN
|
||||
};
|
||||
|
||||
enum acpi_pld_vertical_position {
|
||||
PLD_VERTICAL_POSITION_UPPER,
|
||||
PLD_VERTICAL_POSITION_CENTER,
|
||||
PLD_VERTICAL_POSITION_LOWER
|
||||
};
|
||||
|
||||
/*
|
||||
* The ACPI spec 6.2A does not define the horizontal position field.
|
||||
* These values are taken from the IASL compiler:
|
||||
* https://github.com/acpica/acpica/blob/master/source/components/utilities/utglobal.c#L321
|
||||
*/
|
||||
|
||||
enum acpi_pld_horizontal_position {
|
||||
PLD_HORIZONTAL_POSITION_LEFT,
|
||||
PLD_HORIZONTAL_POSITION_CENTER,
|
||||
PLD_HORIZONTAL_POSITION_RIGHT
|
||||
};
|
||||
|
||||
enum acpi_pld_shape {
|
||||
PLD_SHAPE_ROUND,
|
||||
PLD_SHAPE_OVAL,
|
||||
PLD_SHAPE_SQUARE,
|
||||
PLD_SHAPE_VERTICAL_RECTANGLE,
|
||||
PLD_SHAPE_HORIZONTAL_RECTANGLE,
|
||||
PLD_SHAPE_VERTICAL_TRAPEZOID,
|
||||
PLD_SHAPE_HORIZONTAL_TRAPEZOID,
|
||||
PLD_SHAPE_UNKNOWN,
|
||||
PLD_SHAPE_CHAMFERED
|
||||
};
|
||||
|
||||
enum acpi_pld_orientation {
|
||||
PLD_ORIENTATION_HORIZONTAL,
|
||||
PLD_ORIENTATION_VERTICAL,
|
||||
};
|
||||
|
||||
enum acpi_pld_rotate {
|
||||
PLD_ROTATE_0,
|
||||
PLD_ROTATE_45,
|
||||
PLD_ROTATE_90,
|
||||
PLD_ROTATE_135,
|
||||
PLD_ROTATE_180,
|
||||
PLD_ROTATE_225,
|
||||
PLD_ROTATE_270,
|
||||
PLD_ROTATE_315
|
||||
};
|
||||
|
||||
#define ACPI_PLD_GROUP(__token, __position) \
|
||||
{ \
|
||||
.token = __token, \
|
||||
.position = __position, \
|
||||
}
|
||||
|
||||
struct acpi_pld_group {
|
||||
uint8_t token;
|
||||
uint8_t position;
|
||||
};
|
||||
|
||||
struct acpi_pld {
|
||||
/* Color field can be explicitly ignored */
|
||||
bool ignore_color;
|
||||
uint8_t color_red;
|
||||
uint8_t color_blue;
|
||||
uint8_t color_green;
|
||||
|
||||
/* Port characteristics */
|
||||
bool visible; /* Can be seen by the user */
|
||||
bool lid; /* Port is on lid of device */
|
||||
bool dock; /* Port is in a docking station */
|
||||
bool bay; /* Port is in a bay */
|
||||
bool ejectable; /* Device is ejectable, has _EJx objects */
|
||||
bool ejectable_ospm; /* Device needs OSPM to eject */
|
||||
uint16_t width; /* Width in mm */
|
||||
uint16_t height; /* Height in mm */
|
||||
uint16_t vertical_offset;
|
||||
uint16_t horizontal_offset;
|
||||
enum acpi_pld_panel panel;
|
||||
enum acpi_pld_horizontal_position horizontal_position;
|
||||
enum acpi_pld_vertical_position vertical_position;
|
||||
enum acpi_pld_shape shape;
|
||||
enum acpi_pld_rotate rotation;
|
||||
|
||||
/* Port grouping */
|
||||
enum acpi_pld_orientation orientation;
|
||||
struct acpi_pld_group group;
|
||||
uint8_t draw_order;
|
||||
uint8_t cabinet_number;
|
||||
uint8_t card_cage_number;
|
||||
|
||||
/* Set if this PLD defines a reference shape */
|
||||
bool reference_shape;
|
||||
};
|
||||
|
||||
/* Fill out PLD structure with defaults based on USB port type */
|
||||
int acpi_pld_fill_usb(struct acpi_pld *pld, enum acpi_upc_type type,
|
||||
struct acpi_pld_group *group);
|
||||
|
||||
/* Turn PLD structure into a 20 byte ACPI buffer */
|
||||
int acpi_pld_to_buffer(const struct acpi_pld *pld, uint8_t *buf, int buf_len);
|
||||
|
||||
#endif
|
||||
#include <acpi/acpi_pld.h>
|
||||
|
|
|
@ -1,490 +1,4 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
#ifndef LIBACPI_H
|
||||
#define LIBACPI_H
|
||||
|
||||
#include <stdint.h>
|
||||
#include <arch/acpi.h>
|
||||
#include <arch/acpi_device.h>
|
||||
#include <arch/acpi_pld.h>
|
||||
#include <device/pci_type.h>
|
||||
|
||||
/* Values that can be returned for ACPI Device _STA method */
|
||||
#define ACPI_STATUS_DEVICE_PRESENT (1 << 0)
|
||||
#define ACPI_STATUS_DEVICE_ENABLED (1 << 1)
|
||||
#define ACPI_STATUS_DEVICE_SHOW_IN_UI (1 << 2)
|
||||
#define ACPI_STATUS_DEVICE_STATE_OK (1 << 3)
|
||||
|
||||
#define ACPI_STATUS_DEVICE_ALL_OFF 0
|
||||
#define ACPI_STATUS_DEVICE_ALL_ON (ACPI_STATUS_DEVICE_PRESENT |\
|
||||
ACPI_STATUS_DEVICE_ENABLED |\
|
||||
ACPI_STATUS_DEVICE_SHOW_IN_UI |\
|
||||
ACPI_STATUS_DEVICE_STATE_OK)
|
||||
#define ACPI_STATUS_DEVICE_HIDDEN_ON (ACPI_STATUS_DEVICE_PRESENT |\
|
||||
ACPI_STATUS_DEVICE_ENABLED |\
|
||||
ACPI_STATUS_DEVICE_STATE_OK)
|
||||
|
||||
/* ACPI Op/Prefix Codes */
|
||||
enum {
|
||||
ZERO_OP = 0x00,
|
||||
ONE_OP = 0x01,
|
||||
ALIAS_OP = 0x06,
|
||||
NAME_OP = 0x08,
|
||||
BYTE_PREFIX = 0x0A,
|
||||
WORD_PREFIX = 0x0B,
|
||||
DWORD_PREFIX = 0x0C,
|
||||
STRING_PREFIX = 0x0D,
|
||||
QWORD_PREFIX = 0x0E,
|
||||
SCOPE_OP = 0x10,
|
||||
BUFFER_OP = 0x11,
|
||||
PACKAGE_OP = 0x12,
|
||||
VARIABLE_PACKAGE_OP = 0x13,
|
||||
METHOD_OP = 0x14,
|
||||
EXTERNAL_OP = 0x15,
|
||||
DUAL_NAME_PREFIX = 0x2E,
|
||||
MULTI_NAME_PREFIX = 0x2F,
|
||||
EXT_OP_PREFIX = 0x5B,
|
||||
MUTEX_OP = 0x01,
|
||||
EVENT_OP = 0x01,
|
||||
SF_RIGHT_OP = 0x10,
|
||||
SF_LEFT_OP = 0x11,
|
||||
COND_REFOF_OP = 0x12,
|
||||
CREATEFIELD_OP = 0x13,
|
||||
LOAD_TABLE_OP = 0x1f,
|
||||
LOAD_OP = 0x20,
|
||||
STALL_OP = 0x21,
|
||||
SLEEP_OP = 0x22,
|
||||
ACQUIRE_OP = 0x23,
|
||||
SIGNAL_OP = 0x24,
|
||||
WAIT_OP = 0x25,
|
||||
RST_OP = 0x26,
|
||||
RELEASE_OP = 0x27,
|
||||
FROM_BCD_OP = 0x28,
|
||||
TO_BCD_OP = 0x29,
|
||||
UNLOAD_OP = 0x2A,
|
||||
REVISON_OP = 0x30,
|
||||
DEBUG_OP = 0x31,
|
||||
FATAL_OP = 0x32,
|
||||
TIMER_OP = 0x33,
|
||||
OPREGION_OP = 0x80,
|
||||
FIELD_OP = 0x81,
|
||||
DEVICE_OP = 0x82,
|
||||
PROCESSOR_OP = 0x83,
|
||||
POWER_RES_OP = 0x84,
|
||||
THERMAL_ZONE_OP = 0x85,
|
||||
INDEX_FIELD_OP = 0x86,
|
||||
BANK_FIELD_OP = 0x87,
|
||||
DATA_REGION_OP = 0x88,
|
||||
ROOT_PREFIX = 0x5C,
|
||||
PARENT_PREFIX = 0x5E,
|
||||
LOCAL0_OP = 0x60,
|
||||
LOCAL1_OP = 0x61,
|
||||
LOCAL2_OP = 0x62,
|
||||
LOCAL3_OP = 0x63,
|
||||
LOCAL4_OP = 0x64,
|
||||
LOCAL5_OP = 0x65,
|
||||
LOCAL6_OP = 0x66,
|
||||
LOCAL7_OP = 0x67,
|
||||
ARG0_OP = 0x68,
|
||||
ARG1_OP = 0x69,
|
||||
ARG2_OP = 0x6A,
|
||||
ARG3_OP = 0x6B,
|
||||
ARG4_OP = 0x6C,
|
||||
ARG5_OP = 0x6D,
|
||||
ARG6_OP = 0x6E,
|
||||
STORE_OP = 0x70,
|
||||
REF_OF_OP = 0x71,
|
||||
ADD_OP = 0x72,
|
||||
CONCATENATE_OP = 0x73,
|
||||
SUBTRACT_OP = 0x74,
|
||||
INCREMENT_OP = 0x75,
|
||||
DECREMENT_OP = 0x76,
|
||||
MULTIPLY_OP = 0x77,
|
||||
DIVIDE_OP = 0x78,
|
||||
SHIFT_LEFT_OP = 0x79,
|
||||
SHIFT_RIGHT_OP = 0x7A,
|
||||
AND_OP = 0x7B,
|
||||
NAND_OP = 0x7C,
|
||||
OR_OP = 0x7D,
|
||||
NOR_OP = 0x7E,
|
||||
XOR_OP = 0x7F,
|
||||
NOT_OP = 0x80,
|
||||
FD_SHIFT_LEFT_BIT_OR = 0x81,
|
||||
FD_SHIFT_RIGHT_BIT_OR = 0x82,
|
||||
DEREF_OP = 0x83,
|
||||
CONCATENATE_TEMP_OP = 0x84,
|
||||
MOD_OP = 0x85,
|
||||
NOTIFY_OP = 0x86,
|
||||
SIZEOF_OP = 0x87,
|
||||
INDEX_OP = 0x88,
|
||||
MATCH_OP = 0x89,
|
||||
CREATE_DWORD_OP = 0x8A,
|
||||
CREATE_WORD_OP = 0x8B,
|
||||
CREATE_BYTE_OP = 0x8C,
|
||||
CREATE_BIT_OP = 0x8D,
|
||||
OBJ_TYPE_OP = 0x8E,
|
||||
CREATE_QWORD_OP = 0x8F,
|
||||
LAND_OP = 0x90,
|
||||
LOR_OP = 0x91,
|
||||
LNOT_OP = 0x92,
|
||||
LEQUAL_OP = 0x93,
|
||||
LGREATER_OP = 0x94,
|
||||
LLESS_OP = 0x95,
|
||||
TO_BUFFER_OP = 0x96,
|
||||
TO_DEC_STRING_OP = 0x97,
|
||||
TO_HEX_STRING_OP = 0x98,
|
||||
TO_INTEGER_OP = 0x99,
|
||||
TO_STRING_OP = 0x9C,
|
||||
CP_OBJ_OP = 0x9D,
|
||||
MID_OP = 0x9E,
|
||||
CONTINUE_OP = 0x9F,
|
||||
IF_OP = 0xA0,
|
||||
ELSE_OP = 0xA1,
|
||||
WHILE_OP = 0xA2,
|
||||
NOOP_OP = 0xA3,
|
||||
RETURN_OP = 0xA4,
|
||||
BREAK_OP = 0xA5,
|
||||
COMMENT_OP = 0xA9,
|
||||
BREAKPIONT_OP = 0xCC,
|
||||
ONES_OP = 0xFF,
|
||||
};
|
||||
|
||||
#define FIELDLIST_OFFSET(X) { .type = OFFSET, \
|
||||
.name = "",\
|
||||
.bits = X * 8, \
|
||||
}
|
||||
#define FIELDLIST_NAMESTR(X, Y) { .type = NAME_STRING, \
|
||||
.name = X, \
|
||||
.bits = Y, \
|
||||
}
|
||||
|
||||
#define FIELD_ANYACC 0
|
||||
#define FIELD_BYTEACC 1
|
||||
#define FIELD_WORDACC 2
|
||||
#define FIELD_DWORDACC 3
|
||||
#define FIELD_QWORDACC 4
|
||||
#define FIELD_BUFFERACC 5
|
||||
#define FIELD_NOLOCK (0<<4)
|
||||
#define FIELD_LOCK (1<<4)
|
||||
#define FIELD_PRESERVE (0<<5)
|
||||
#define FIELD_WRITEASONES (1<<5)
|
||||
#define FIELD_WRITEASZEROS (2<<5)
|
||||
|
||||
enum field_type {
|
||||
OFFSET,
|
||||
NAME_STRING,
|
||||
FIELD_TYPE_MAX,
|
||||
};
|
||||
|
||||
struct fieldlist {
|
||||
enum field_type type;
|
||||
const char *name;
|
||||
u32 bits;
|
||||
};
|
||||
|
||||
#define OPREGION(rname, space, offset, len) {.name = rname, \
|
||||
.regionspace = space, \
|
||||
.regionoffset = offset, \
|
||||
.regionlen = len, \
|
||||
}
|
||||
|
||||
enum region_space {
|
||||
SYSTEMMEMORY,
|
||||
SYSTEMIO,
|
||||
PCI_CONFIG,
|
||||
EMBEDDEDCONTROL,
|
||||
SMBUS,
|
||||
CMOS,
|
||||
PCIBARTARGET,
|
||||
IPMI,
|
||||
GPIO_REGION,
|
||||
GPSERIALBUS,
|
||||
PCC,
|
||||
FIXED_HARDWARE = 0x7F,
|
||||
REGION_SPACE_MAX,
|
||||
};
|
||||
|
||||
struct opregion {
|
||||
const char *name;
|
||||
enum region_space regionspace;
|
||||
unsigned long regionoffset;
|
||||
unsigned long regionlen;
|
||||
};
|
||||
|
||||
#define DSM_UUID(DSM_UUID, DSM_CALLBACKS, DSM_COUNT, DSM_ARG) \
|
||||
{ .uuid = DSM_UUID, \
|
||||
.callbacks = DSM_CALLBACKS, \
|
||||
.count = DSM_COUNT, \
|
||||
.arg = DSM_ARG, \
|
||||
}
|
||||
|
||||
struct dsm_uuid {
|
||||
const char *uuid;
|
||||
void (**callbacks)(void *);
|
||||
size_t count;
|
||||
void *arg;
|
||||
};
|
||||
|
||||
/*version 1 has 15 fields, version 2 has 19, and version 3 has 21 */
|
||||
enum cppc_fields {
|
||||
CPPC_HIGHEST_PERF, /* can be DWORD */
|
||||
CPPC_NOMINAL_PERF, /* can be DWORD */
|
||||
CPPC_LOWEST_NONL_PERF, /* can be DWORD */
|
||||
CPPC_LOWEST_PERF, /* can be DWORD */
|
||||
CPPC_GUARANTEED_PERF,
|
||||
CPPC_DESIRED_PERF,
|
||||
CPPC_MIN_PERF,
|
||||
CPPC_MAX_PERF,
|
||||
CPPC_PERF_REDUCE_TOLERANCE,
|
||||
CPPC_TIME_WINDOW,
|
||||
CPPC_COUNTER_WRAP, /* can be DWORD */
|
||||
CPPC_REF_PERF_COUNTER,
|
||||
CPPC_DELIVERED_PERF_COUNTER,
|
||||
CPPC_PERF_LIMITED,
|
||||
CPPC_ENABLE, /* can be System I/O */
|
||||
CPPC_MAX_FIELDS_VER_1,
|
||||
CPPC_AUTO_SELECT = /* can be DWORD */
|
||||
CPPC_MAX_FIELDS_VER_1,
|
||||
CPPC_AUTO_ACTIVITY_WINDOW,
|
||||
CPPC_PERF_PREF,
|
||||
CPPC_REF_PERF, /* can be DWORD */
|
||||
CPPC_MAX_FIELDS_VER_2,
|
||||
CPPC_LOWEST_FREQ = /* can be DWORD */
|
||||
CPPC_MAX_FIELDS_VER_2,
|
||||
CPPC_NOMINAL_FREQ, /* can be DWORD */
|
||||
CPPC_MAX_FIELDS_VER_3,
|
||||
};
|
||||
|
||||
struct cppc_config {
|
||||
u32 version; /* must be 1, 2, or 3 */
|
||||
/*
|
||||
* The generic acpi_addr_t structure is being used, though
|
||||
* anything besides PPC or FFIXED generally requires checking
|
||||
* if the OS has advertised support for it (via _OSC).
|
||||
*
|
||||
* NOTE: some fields permit DWORDs to be used. If you
|
||||
* provide a System Memory register with all zeros (which
|
||||
* represents unsupported) then this will be used as-is.
|
||||
* Otherwise, a System Memory register with a 32-bit
|
||||
* width will be converted into a DWORD field (the value
|
||||
* of which will be the value of 'addrl'. Any other use
|
||||
* of System Memory register is currently undefined.
|
||||
* (i.e., if you have an actual need for System Memory
|
||||
* then you'll need to adjust this kludge).
|
||||
*/
|
||||
acpi_addr_t regs[CPPC_MAX_FIELDS_VER_3];
|
||||
};
|
||||
|
||||
void acpigen_write_return_integer(uint64_t arg);
|
||||
void acpigen_write_return_string(const char *arg);
|
||||
void acpigen_write_len_f(void);
|
||||
void acpigen_pop_len(void);
|
||||
void acpigen_set_current(char *curr);
|
||||
char *acpigen_get_current(void);
|
||||
char *acpigen_write_package(int nr_el);
|
||||
void acpigen_write_zero(void);
|
||||
void acpigen_write_one(void);
|
||||
void acpigen_write_ones(void);
|
||||
void acpigen_write_byte(unsigned int data);
|
||||
void acpigen_emit_byte(unsigned char data);
|
||||
void acpigen_emit_ext_op(uint8_t op);
|
||||
void acpigen_emit_word(unsigned int data);
|
||||
void acpigen_emit_dword(unsigned int data);
|
||||
void acpigen_emit_stream(const char *data, int size);
|
||||
void acpigen_emit_string(const char *string);
|
||||
void acpigen_emit_namestring(const char *namepath);
|
||||
void acpigen_emit_eisaid(const char *eisaid);
|
||||
void acpigen_write_word(unsigned int data);
|
||||
void acpigen_write_dword(unsigned int data);
|
||||
void acpigen_write_qword(uint64_t data);
|
||||
void acpigen_write_integer(uint64_t data);
|
||||
void acpigen_write_string(const char *string);
|
||||
void acpigen_write_name_unicode(const char *name, const char *string);
|
||||
void acpigen_write_name(const char *name);
|
||||
void acpigen_write_name_zero(const char *name);
|
||||
void acpigen_write_name_one(const char *name);
|
||||
void acpigen_write_name_string(const char *name, const char *string);
|
||||
void acpigen_write_name_dword(const char *name, uint32_t val);
|
||||
void acpigen_write_name_qword(const char *name, uint64_t val);
|
||||
void acpigen_write_name_byte(const char *name, uint8_t val);
|
||||
void acpigen_write_name_integer(const char *name, uint64_t val);
|
||||
void acpigen_write_coreboot_hid(enum coreboot_acpi_ids id);
|
||||
void acpigen_write_scope(const char *name);
|
||||
void acpigen_write_method(const char *name, int nargs);
|
||||
void acpigen_write_method_serialized(const char *name, int nargs);
|
||||
void acpigen_write_device(const char *name);
|
||||
void acpigen_write_PPC(u8 nr);
|
||||
void acpigen_write_PPC_NVS(void);
|
||||
void acpigen_write_empty_PCT(void);
|
||||
void acpigen_write_empty_PTC(void);
|
||||
void acpigen_write_PRW(u32 wake, u32 level);
|
||||
void acpigen_write_STA(uint8_t status);
|
||||
void acpigen_write_TPC(const char *gnvs_tpc_limit);
|
||||
void acpigen_write_PSS_package(u32 coreFreq, u32 power, u32 transLat,
|
||||
u32 busmLat, u32 control, u32 status);
|
||||
typedef enum { SW_ALL = 0xfc, SW_ANY = 0xfd, HW_ALL = 0xfe } PSD_coord;
|
||||
void acpigen_write_PSD_package(u32 domain, u32 numprocs, PSD_coord coordtype);
|
||||
void acpigen_write_CST_package_entry(acpi_cstate_t *cstate);
|
||||
void acpigen_write_CST_package(acpi_cstate_t *entry, int nentries);
|
||||
typedef enum { CSD_HW_ALL = 0xfe } CSD_coord;
|
||||
void acpigen_write_CSD_package(u32 domain, u32 numprocs, CSD_coord coordtype,
|
||||
u32 index);
|
||||
void acpigen_write_processor(u8 cpuindex, u32 pblock_addr, u8 pblock_len);
|
||||
void acpigen_write_processor_package(const char *name,
|
||||
unsigned int first_core,
|
||||
unsigned int core_count);
|
||||
void acpigen_write_processor_cnot(const unsigned int number_of_cores);
|
||||
void acpigen_write_TSS_package(int entries, acpi_tstate_t *tstate_list);
|
||||
void acpigen_write_TSD_package(u32 domain, u32 numprocs, PSD_coord coordtype);
|
||||
void acpigen_write_mem32fixed(int readwrite, u32 base, u32 size);
|
||||
void acpigen_write_io16(u16 min, u16 max, u8 align, u8 len, u8 decode16);
|
||||
void acpigen_write_register_resource(const acpi_addr_t *addr);
|
||||
void acpigen_write_resourcetemplate_header(void);
|
||||
void acpigen_write_resourcetemplate_footer(void);
|
||||
void acpigen_write_mainboard_resource_template(void);
|
||||
void acpigen_write_mainboard_resources(const char *scope, const char *name);
|
||||
void acpigen_write_irq(u16 mask);
|
||||
void acpigen_write_uuid(const char *uuid);
|
||||
void acpigen_write_power_res(const char *name, uint8_t level, uint16_t order,
|
||||
const char * const dev_states[], size_t dev_states_count);
|
||||
void acpigen_write_sleep(uint64_t sleep_ms);
|
||||
void acpigen_write_store(void);
|
||||
void acpigen_write_store_ops(uint8_t src, uint8_t dst);
|
||||
void acpigen_write_store_op_to_namestr(uint8_t src, const char *dst);
|
||||
void acpigen_write_or(uint8_t arg1, uint8_t arg2, uint8_t res);
|
||||
void acpigen_write_xor(uint8_t arg1, uint8_t arg2, uint8_t res);
|
||||
void acpigen_write_and(uint8_t arg1, uint8_t arg2, uint8_t res);
|
||||
void acpigen_write_not(uint8_t arg, uint8_t res);
|
||||
void acpigen_write_debug_string(const char *str);
|
||||
void acpigen_write_debug_integer(uint64_t val);
|
||||
void acpigen_write_debug_op(uint8_t op);
|
||||
void acpigen_write_if(void);
|
||||
void acpigen_write_if_and(uint8_t arg1, uint8_t arg2);
|
||||
void acpigen_write_if_lequal_op_int(uint8_t op, uint64_t val);
|
||||
void acpigen_write_if_lequal_namestr_int(const char *namestr, uint64_t val);
|
||||
void acpigen_write_else(void);
|
||||
void acpigen_write_to_buffer(uint8_t src, uint8_t dst);
|
||||
void acpigen_write_to_integer(uint8_t src, uint8_t dst);
|
||||
void acpigen_write_byte_buffer(uint8_t *arr, size_t size);
|
||||
void acpigen_write_return_byte_buffer(uint8_t *arr, size_t size);
|
||||
void acpigen_write_return_singleton_buffer(uint8_t arg);
|
||||
void acpigen_write_return_byte(uint8_t arg);
|
||||
void acpigen_write_upc(enum acpi_upc_type type);
|
||||
void acpigen_write_pld(const struct acpi_pld *pld);
|
||||
void acpigen_write_ADR(uint64_t adr);
|
||||
void acpigen_write_ADR_pci_devfn(pci_devfn_t devfn);
|
||||
void acpigen_write_ADR_pci_device(const struct device *dev);
|
||||
/*
|
||||
* Generate ACPI AML code for _DSM method.
|
||||
* This function takes as input uuid for the device, set of callbacks and
|
||||
* argument to pass into the callbacks. Callbacks should ensure that Local0 and
|
||||
* Local1 are left untouched. Use of Local2-Local7 is permitted in callbacks.
|
||||
*/
|
||||
void acpigen_write_dsm(const char *uuid, void (**callbacks)(void *),
|
||||
size_t count, void *arg);
|
||||
void acpigen_write_dsm_uuid_arr(struct dsm_uuid *ids, size_t count);
|
||||
|
||||
/*
|
||||
* Generate ACPI AML code for _CPC (Continuous Performance Control).
|
||||
* Execute the package function once to create a global table, then
|
||||
* execute the method function within each processor object to
|
||||
* create a method that points to the global table.
|
||||
*/
|
||||
void acpigen_write_CPPC_package(const struct cppc_config *config);
|
||||
void acpigen_write_CPPC_method(void);
|
||||
|
||||
/*
|
||||
* Generate ACPI AML code for _ROM method.
|
||||
* This function takes as input ROM data and ROM length.
|
||||
* The ROM length has to be multiple of 4096 and has to be less
|
||||
* than the current implementation limit of 0x40000.
|
||||
*/
|
||||
void acpigen_write_rom(void *bios, const size_t length);
|
||||
/*
|
||||
* Generate ACPI AML code for OperationRegion
|
||||
* This function takes input region name, region space, region offset & region
|
||||
* length.
|
||||
*/
|
||||
void acpigen_write_opregion(struct opregion *opreg);
|
||||
/*
|
||||
* Generate ACPI AML code for Mutex
|
||||
* This function takes mutex name and initial value.
|
||||
*/
|
||||
void acpigen_write_mutex(const char *name, const uint8_t flags);
|
||||
/*
|
||||
* Generate ACPI AML code for Acquire
|
||||
* This function takes mutex name and privilege value.
|
||||
*/
|
||||
void acpigen_write_acquire(const char *name, const uint16_t val);
|
||||
/*
|
||||
* Generate ACPI AML code for Release
|
||||
* This function takes mutex name.
|
||||
*/
|
||||
void acpigen_write_release(const char *name);
|
||||
/*
|
||||
* Generate ACPI AML code for Field
|
||||
* This function takes input region name, fieldlist, count & flags.
|
||||
*/
|
||||
void acpigen_write_field(const char *name, const struct fieldlist *l, size_t count,
|
||||
uint8_t flags);
|
||||
/*
|
||||
* Generate ACPI AML code for IndexField
|
||||
* This function takes input index name, data name, fieldlist, count & flags.
|
||||
*/
|
||||
void acpigen_write_indexfield(const char *idx, const char *data,
|
||||
struct fieldlist *l, size_t count, uint8_t flags);
|
||||
|
||||
int get_cst_entries(acpi_cstate_t **);
|
||||
|
||||
/*
|
||||
* Soc-implemented functions for generating ACPI AML code for GPIO handling. All
|
||||
* these functions are expected to use only Local5, Local6 and Local7
|
||||
* variables. If the functions call into another ACPI method, then there is no
|
||||
* restriction on the use of Local variables. In case of get/read functions,
|
||||
* return value is expected to be stored in Local0 variable.
|
||||
*
|
||||
* All functions return 0 on success and -1 on error.
|
||||
*/
|
||||
|
||||
/* Generate ACPI AML code to return Rx value of GPIO in Local0. */
|
||||
int acpigen_soc_read_rx_gpio(unsigned int gpio_num);
|
||||
|
||||
/* Generate ACPI AML code to return Tx value of GPIO in Local0. */
|
||||
int acpigen_soc_get_tx_gpio(unsigned int gpio_num);
|
||||
|
||||
/* Generate ACPI AML code to set Tx value of GPIO to 1. */
|
||||
int acpigen_soc_set_tx_gpio(unsigned int gpio_num);
|
||||
|
||||
/* Generate ACPI AML code to set Tx value of GPIO to 0. */
|
||||
int acpigen_soc_clear_tx_gpio(unsigned int gpio_num);
|
||||
|
||||
/*
|
||||
* Helper functions for enabling/disabling Tx GPIOs based on the GPIO
|
||||
* polarity. These functions end up calling acpigen_soc_{set,clear}_tx_gpio to
|
||||
* make callbacks into SoC acpigen code.
|
||||
*
|
||||
* Returns 0 on success and -1 on error.
|
||||
*/
|
||||
int acpigen_enable_tx_gpio(struct acpi_gpio *gpio);
|
||||
int acpigen_disable_tx_gpio(struct acpi_gpio *gpio);
|
||||
|
||||
/*
|
||||
* Helper function for getting a RX GPIO value based on the GPIO polarity.
|
||||
* The return value is stored in Local0 variable.
|
||||
* This function ends up calling acpigen_soc_get_rx_gpio to make callbacks
|
||||
* into SoC acpigen code
|
||||
*/
|
||||
void acpigen_get_rx_gpio(struct acpi_gpio *gpio);
|
||||
|
||||
/* refer to ACPI 6.4.3.5.3 Word Address Space Descriptor section for details */
|
||||
void acpigen_resource_word(u16 res_type, u16 gen_flags, u16 type_flags, u16 gran,
|
||||
u16 range_min, u16 range_max, u16 translation, u16 length);
|
||||
/* refer to ACPI 6.4.3.5.2 DWord Address Space Descriptor section for details */
|
||||
void acpigen_resource_dword(u16 res_type, u16 gen_flags, u16 type_flags,
|
||||
u32 gran, u32 range_min, u32 range_max, u32 translation, u32 length);
|
||||
/* refer to ACPI 6.4.3.5.1 QWord Address Space Descriptor section for details */
|
||||
void acpigen_resource_qword(u16 res_type, u16 gen_flags, u16 type_flags,
|
||||
u64 gran, u64 range_min, u64 range_max, u64 translation, u64 length);
|
||||
|
||||
#endif
|
||||
#include <acpi/acpigen.h>
|
||||
|
|
|
@ -1,15 +1,4 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
#ifndef __ARCH_ACPIGEN_DSM_H__
|
||||
#define __ARCH_ACPIGEN_DSM_H__
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
struct dsm_i2c_hid_config {
|
||||
uint8_t hid_desc_reg_offset;
|
||||
};
|
||||
|
||||
void acpigen_write_dsm_i2c_hid(struct dsm_i2c_hid_config *config);
|
||||
|
||||
#endif /* __ARCH_ACPIGEN_DSM_H__ */
|
||||
#include <acpi/acpigen_dsm.h>
|
||||
|
|
|
@ -4,38 +4,4 @@
|
|||
* SPDX-License-Identifier: GPL-2.0-or-later
|
||||
*/
|
||||
|
||||
#ifndef __ACPIGEN_PS2_KEYBD_H__
|
||||
#define __ACPIGEN_PS2_KEYBD_H__
|
||||
|
||||
#include <types.h>
|
||||
|
||||
enum ps2_action_key {
|
||||
PS2_KEY_ABSENT = 0,
|
||||
PS2_KEY_BACK,
|
||||
PS2_KEY_FORWARD,
|
||||
PS2_KEY_REFRESH,
|
||||
PS2_KEY_FULLSCREEN,
|
||||
PS2_KEY_OVERVIEW,
|
||||
PS2_KEY_BRIGHTNESS_DOWN,
|
||||
PS2_KEY_BRIGHTNESS_UP,
|
||||
PS2_KEY_VOL_MUTE,
|
||||
PS2_KEY_VOL_DOWN,
|
||||
PS2_KEY_VOL_UP,
|
||||
PS2_KEY_SNAPSHOT,
|
||||
PS2_KEY_PRIVACY_SCRN_TOGGLE,
|
||||
PS2_KEY_KBD_BKLIGHT_DOWN,
|
||||
PS2_KEY_KBD_BKLIGHT_UP,
|
||||
PS2_KEY_PLAY_PAUSE,
|
||||
PS2_KEY_NEXT_TRACK,
|
||||
PS2_KEY_PREV_TRACK,
|
||||
};
|
||||
|
||||
#define PS2_MIN_TOP_ROW_KEYS 10
|
||||
#define PS2_MAX_TOP_ROW_KEYS 15
|
||||
|
||||
void acpigen_ps2_keyboard_dsd(const char *scope, uint8_t num_top_row_keys,
|
||||
enum ps2_action_key action_keys[],
|
||||
bool can_send_function_keys,
|
||||
bool has_numeric_keypad, bool has_scrnlock_key);
|
||||
|
||||
#endif /* __ACPIGEN_PS2_KEYBD_H__ */
|
||||
#include <acpi/acpigen_ps2_keybd.h>
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,513 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
#ifndef __ACPI_DEVICE_H
|
||||
#define __ACPI_DEVICE_H
|
||||
|
||||
#include <device/i2c.h>
|
||||
#include <stdint.h>
|
||||
#include <spi-generic.h>
|
||||
|
||||
enum acpi_dp_type {
|
||||
ACPI_DP_TYPE_UNKNOWN,
|
||||
ACPI_DP_TYPE_INTEGER,
|
||||
ACPI_DP_TYPE_STRING,
|
||||
ACPI_DP_TYPE_REFERENCE,
|
||||
ACPI_DP_TYPE_TABLE,
|
||||
ACPI_DP_TYPE_ARRAY,
|
||||
ACPI_DP_TYPE_CHILD,
|
||||
};
|
||||
|
||||
struct acpi_dp {
|
||||
enum acpi_dp_type type;
|
||||
const char *name;
|
||||
struct acpi_dp *next;
|
||||
union {
|
||||
struct acpi_dp *child;
|
||||
struct acpi_dp *array;
|
||||
};
|
||||
union {
|
||||
uint64_t integer;
|
||||
const char *string;
|
||||
};
|
||||
};
|
||||
|
||||
#define ACPI_DESCRIPTOR_LARGE (1 << 7)
|
||||
#define ACPI_DESCRIPTOR_INTERRUPT (ACPI_DESCRIPTOR_LARGE | 9)
|
||||
#define ACPI_DESCRIPTOR_GPIO (ACPI_DESCRIPTOR_LARGE | 12)
|
||||
#define ACPI_DESCRIPTOR_SERIAL_BUS (ACPI_DESCRIPTOR_LARGE | 14)
|
||||
|
||||
/*
|
||||
* PRP0001 is a special DT namespace link device ID. It provides a means to use
|
||||
* existing DT-compatible device identification in ACPI. When this _HID is used
|
||||
* by an ACPI device, the ACPI subsystem in OS looks up "compatible" property in
|
||||
* device object's _DSD and will use the value of that property to identify the
|
||||
* corresponding device in analogy with the original DT device identification
|
||||
* algorithm.
|
||||
* More details can be found in Linux kernel documentation:
|
||||
* Documentation/acpi/enumeration.txt
|
||||
*/
|
||||
#define ACPI_DT_NAMESPACE_HID "PRP0001"
|
||||
|
||||
struct device;
|
||||
const char *acpi_device_name(const struct device *dev);
|
||||
const char *acpi_device_hid(const struct device *dev);
|
||||
uint32_t acpi_device_uid(const struct device *dev);
|
||||
const char *acpi_device_path(const struct device *dev);
|
||||
const char *acpi_device_scope(const struct device *dev);
|
||||
const char *acpi_device_path_join(const struct device *dev, const char *name);
|
||||
int acpi_device_status(const struct device *dev);
|
||||
void acpi_device_write_uid(const struct device *dev);
|
||||
|
||||
/*
|
||||
* ACPI Descriptor for extended Interrupt()
|
||||
*/
|
||||
|
||||
enum acpi_irq_mode {
|
||||
ACPI_IRQ_EDGE_TRIGGERED,
|
||||
ACPI_IRQ_LEVEL_TRIGGERED
|
||||
};
|
||||
|
||||
enum acpi_irq_polarity {
|
||||
ACPI_IRQ_ACTIVE_LOW,
|
||||
ACPI_IRQ_ACTIVE_HIGH,
|
||||
ACPI_IRQ_ACTIVE_BOTH
|
||||
};
|
||||
|
||||
enum acpi_irq_shared {
|
||||
ACPI_IRQ_EXCLUSIVE,
|
||||
ACPI_IRQ_SHARED
|
||||
};
|
||||
|
||||
enum acpi_irq_wake {
|
||||
ACPI_IRQ_NO_WAKE,
|
||||
ACPI_IRQ_WAKE
|
||||
};
|
||||
|
||||
struct acpi_irq {
|
||||
unsigned int pin;
|
||||
enum acpi_irq_mode mode;
|
||||
enum acpi_irq_polarity polarity;
|
||||
enum acpi_irq_shared shared;
|
||||
enum acpi_irq_wake wake;
|
||||
};
|
||||
|
||||
#define ACPI_IRQ_CFG(_pin, _mode, _pol, _shared, _wake) { \
|
||||
.pin = (_pin), \
|
||||
.mode = (_mode), \
|
||||
.polarity = (_pol), \
|
||||
.shared = (_shared), \
|
||||
.wake = (_wake) }
|
||||
|
||||
#define ACPI_IRQ_EDGE_LOW(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_EDGE_TRIGGERED, ACPI_IRQ_ACTIVE_LOW, \
|
||||
ACPI_IRQ_EXCLUSIVE, ACPI_IRQ_NO_WAKE)
|
||||
|
||||
#define ACPI_IRQ_EDGE_HIGH(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_EDGE_TRIGGERED, ACPI_IRQ_ACTIVE_HIGH, \
|
||||
ACPI_IRQ_EXCLUSIVE, ACPI_IRQ_NO_WAKE)
|
||||
|
||||
#define ACPI_IRQ_LEVEL_LOW(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_LEVEL_TRIGGERED, ACPI_IRQ_ACTIVE_LOW, \
|
||||
ACPI_IRQ_SHARED, ACPI_IRQ_NO_WAKE)
|
||||
|
||||
#define ACPI_IRQ_LEVEL_HIGH(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_LEVEL_TRIGGERED, ACPI_IRQ_ACTIVE_HIGH, \
|
||||
ACPI_IRQ_SHARED, ACPI_IRQ_NO_WAKE)
|
||||
|
||||
#define ACPI_IRQ_WAKE_EDGE_LOW(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_EDGE_TRIGGERED, ACPI_IRQ_ACTIVE_LOW, \
|
||||
ACPI_IRQ_EXCLUSIVE, ACPI_IRQ_WAKE)
|
||||
|
||||
#define ACPI_IRQ_WAKE_EDGE_HIGH(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_EDGE_TRIGGERED, ACPI_IRQ_ACTIVE_HIGH, \
|
||||
ACPI_IRQ_EXCLUSIVE, ACPI_IRQ_WAKE)
|
||||
|
||||
#define ACPI_IRQ_WAKE_LEVEL_LOW(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_LEVEL_TRIGGERED, ACPI_IRQ_ACTIVE_LOW, \
|
||||
ACPI_IRQ_SHARED, ACPI_IRQ_WAKE)
|
||||
|
||||
#define ACPI_IRQ_WAKE_LEVEL_HIGH(x) \
|
||||
ACPI_IRQ_CFG((x), ACPI_IRQ_LEVEL_TRIGGERED, ACPI_IRQ_ACTIVE_HIGH, \
|
||||
ACPI_IRQ_SHARED, ACPI_IRQ_WAKE)
|
||||
|
||||
/* Write extended Interrupt() descriptor to SSDT AML output */
|
||||
void acpi_device_write_interrupt(const struct acpi_irq *irq);
|
||||
|
||||
/*
|
||||
* ACPI Descriptors for GpioIo() and GpioInterrupt()
|
||||
*/
|
||||
|
||||
enum acpi_gpio_type {
|
||||
ACPI_GPIO_TYPE_INTERRUPT,
|
||||
ACPI_GPIO_TYPE_IO
|
||||
};
|
||||
|
||||
enum acpi_gpio_pull {
|
||||
ACPI_GPIO_PULL_DEFAULT,
|
||||
ACPI_GPIO_PULL_UP,
|
||||
ACPI_GPIO_PULL_DOWN,
|
||||
ACPI_GPIO_PULL_NONE
|
||||
};
|
||||
|
||||
enum acpi_gpio_io_restrict {
|
||||
ACPI_GPIO_IO_RESTRICT_NONE,
|
||||
ACPI_GPIO_IO_RESTRICT_INPUT,
|
||||
ACPI_GPIO_IO_RESTRICT_OUTPUT,
|
||||
ACPI_GPIO_IO_RESTRICT_PRESERVE
|
||||
};
|
||||
|
||||
enum acpi_gpio_polarity {
|
||||
ACPI_GPIO_ACTIVE_HIGH = 0,
|
||||
ACPI_GPIO_ACTIVE_LOW = 1,
|
||||
};
|
||||
|
||||
#define ACPI_GPIO_REVISION_ID 1
|
||||
#define ACPI_GPIO_MAX_PINS 8
|
||||
|
||||
struct acpi_gpio {
|
||||
int pin_count;
|
||||
uint16_t pins[ACPI_GPIO_MAX_PINS];
|
||||
|
||||
enum acpi_gpio_type type;
|
||||
enum acpi_gpio_pull pull;
|
||||
const char *resource;
|
||||
|
||||
/* GpioInt */
|
||||
uint16_t interrupt_debounce_timeout; /* 1/100 ms */
|
||||
struct acpi_irq irq;
|
||||
|
||||
/* GpioIo */
|
||||
uint16_t output_drive_strength; /* 1/100 mA */
|
||||
int io_shared;
|
||||
enum acpi_gpio_io_restrict io_restrict;
|
||||
enum acpi_gpio_polarity polarity;
|
||||
};
|
||||
|
||||
/* Basic output GPIO with default pull settings */
|
||||
#define ACPI_GPIO_OUTPUT_ACTIVE_HIGH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_IO, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.io_restrict = ACPI_GPIO_IO_RESTRICT_OUTPUT, \
|
||||
.polarity = ACPI_GPIO_ACTIVE_HIGH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
#define ACPI_GPIO_OUTPUT_ACTIVE_LOW(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_IO, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.io_restrict = ACPI_GPIO_IO_RESTRICT_OUTPUT, \
|
||||
.polarity = ACPI_GPIO_ACTIVE_LOW, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Basic input GPIO with default pull settings */
|
||||
#define ACPI_GPIO_INPUT_ACTIVE_HIGH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_IO, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.io_restrict = ACPI_GPIO_IO_RESTRICT_INPUT, \
|
||||
.polarity = ACPI_GPIO_ACTIVE_HIGH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
#define ACPI_GPIO_INPUT_ACTIVE_LOW(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_IO, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.io_restrict = ACPI_GPIO_IO_RESTRICT_INPUT, \
|
||||
.polarity = ACPI_GPIO_ACTIVE_LOW, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active High GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_EDGE_HIGH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_HIGH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active Low GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_EDGE_LOW(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_LOW, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active Both GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_EDGE_BOTH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_BOTH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active High GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_EDGE_HIGH_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_HIGH, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active Low GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_EDGE_LOW_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_LOW, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Edge Triggered Active Both GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_EDGE_BOTH_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_EDGE_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_BOTH, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Level Triggered Active High GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_LEVEL_HIGH(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_LEVEL_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_HIGH, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Level Triggered Active Low GPIO interrupt */
|
||||
#define ACPI_GPIO_IRQ_LEVEL_LOW(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_LEVEL_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_LOW, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Level Triggered Active High GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_LEVEL_HIGH_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_LEVEL_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_HIGH, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Level Triggered Active Low GPIO interrupt with wake */
|
||||
#define ACPI_GPIO_IRQ_LEVEL_LOW_WAKE(gpio) { \
|
||||
.type = ACPI_GPIO_TYPE_INTERRUPT, \
|
||||
.pull = ACPI_GPIO_PULL_DEFAULT, \
|
||||
.irq.mode = ACPI_IRQ_LEVEL_TRIGGERED, \
|
||||
.irq.polarity = ACPI_IRQ_ACTIVE_LOW, \
|
||||
.irq.wake = ACPI_IRQ_WAKE, \
|
||||
.pin_count = 1, \
|
||||
.pins = { (gpio) } }
|
||||
|
||||
/* Write GpioIo() or GpioInt() descriptor to SSDT AML output */
|
||||
void acpi_device_write_gpio(const struct acpi_gpio *gpio);
|
||||
|
||||
/*
|
||||
* ACPI Descriptors for Serial Bus interfaces
|
||||
*/
|
||||
|
||||
#define ACPI_SERIAL_BUS_TYPE_I2C 1
|
||||
#define ACPI_SERIAL_BUS_TYPE_SPI 2
|
||||
#define ACPI_I2C_SERIAL_BUS_REVISION_ID 1 /* TODO: upgrade to 2 */
|
||||
#define ACPI_I2C_TYPE_SPECIFIC_REVISION_ID 1
|
||||
#define ACPI_SPI_SERIAL_BUS_REVISION_ID 1
|
||||
#define ACPI_SPI_TYPE_SPECIFIC_REVISION_ID 1
|
||||
|
||||
/*
|
||||
* ACPI I2C Bus
|
||||
*/
|
||||
|
||||
struct acpi_i2c {
|
||||
/* I2C Address */
|
||||
uint16_t address;
|
||||
/* 7 or 10 bit Address Mode */
|
||||
enum i2c_address_mode mode_10bit;
|
||||
/* I2C Bus Speed in Hz */
|
||||
enum i2c_speed speed;
|
||||
/* Reference to I2C controller */
|
||||
const char *resource;
|
||||
};
|
||||
|
||||
/* Write I2cSerialBus() descriptor to SSDT AML output */
|
||||
void acpi_device_write_i2c(const struct acpi_i2c *i2c);
|
||||
|
||||
/*
|
||||
* ACPI SPI Bus
|
||||
*/
|
||||
|
||||
struct acpi_spi {
|
||||
/* Device selection */
|
||||
uint16_t device_select;
|
||||
/* Device selection line is active high or low */
|
||||
enum spi_polarity device_select_polarity;
|
||||
/* 3 or 4 wire SPI connection */
|
||||
enum spi_wire_mode wire_mode;
|
||||
/* Connection speed in HZ */
|
||||
unsigned int speed;
|
||||
/* Size in bits of smallest transfer unit */
|
||||
u8 data_bit_length;
|
||||
/* Phase of clock pulse on which to capture data */
|
||||
enum spi_clock_phase clock_phase;
|
||||
/* Indicate if clock is high or low during first phase */
|
||||
enum spi_polarity clock_polarity;
|
||||
/* Reference to SPI controller */
|
||||
const char *resource;
|
||||
};
|
||||
|
||||
/* Write SPI Bus descriptor to SSDT AML output */
|
||||
void acpi_device_write_spi(const struct acpi_spi *spi);
|
||||
|
||||
/* GPIO/timing information for the power on/off sequences */
|
||||
struct acpi_power_res_params {
|
||||
/* GPIO used to take device out of reset or to put it into reset. */
|
||||
struct acpi_gpio *reset_gpio;
|
||||
/* Delay to be inserted after device is taken out of reset.
|
||||
* (_ON method delay)
|
||||
*/
|
||||
unsigned int reset_delay_ms;
|
||||
/* Delay to be inserted after device is put into reset.
|
||||
* (_OFF method delay)
|
||||
*/
|
||||
unsigned int reset_off_delay_ms;
|
||||
/* GPIO used to enable device. */
|
||||
struct acpi_gpio *enable_gpio;
|
||||
/* Delay to be inserted after device is enabled.
|
||||
* (_ON method delay)
|
||||
*/
|
||||
unsigned int enable_delay_ms;
|
||||
/* Delay to be inserted after device is disabled.
|
||||
* (_OFF method delay)
|
||||
*/
|
||||
unsigned int enable_off_delay_ms;
|
||||
/* GPIO used to stop operation of device. */
|
||||
struct acpi_gpio *stop_gpio;
|
||||
/* Delay to be inserted after disabling stop.
|
||||
* (_ON method delay)
|
||||
*/
|
||||
unsigned int stop_delay_ms;
|
||||
/* Delay to be inserted after enabling stop.
|
||||
* (_OFF method delay)
|
||||
*/
|
||||
unsigned int stop_off_delay_ms;
|
||||
};
|
||||
|
||||
/*
|
||||
* Add a basic PowerResource block for a device that includes
|
||||
* GPIOs to control enable, reset and stop operation of the device. Each
|
||||
* GPIO is optional, but at least one must be provided.
|
||||
*
|
||||
* Reset - Put the device into / take the device out of reset.
|
||||
* Enable - Enable / disable power to device.
|
||||
* Stop - Stop / start operation of device.
|
||||
*/
|
||||
void acpi_device_add_power_res(const struct acpi_power_res_params *params);
|
||||
|
||||
/*
|
||||
* Writing Device Properties objects via _DSD
|
||||
*
|
||||
* http://uefi.org/sites/default/files/resources/_DSD-device-properties-UUID.pdf
|
||||
* http://uefi.org/sites/default/files/resources/_DSD-hierarchical-data-extension-UUID-v1.pdf
|
||||
*
|
||||
* The Device Property Hierarchy can be multiple levels deep with multiple
|
||||
* children possible in each level. In order to support this flexibility
|
||||
* the device property hierarchy must be built up before being written out.
|
||||
*
|
||||
* For example:
|
||||
*
|
||||
* // Child table with string and integer
|
||||
* struct acpi_dp *child = acpi_dp_new_table("CHLD");
|
||||
* acpi_dp_add_string(child, "childstring", "CHILD");
|
||||
* acpi_dp_add_integer(child, "childint", 100);
|
||||
*
|
||||
* // _DSD table with integer and gpio and child pointer
|
||||
* struct acpi_dp *dsd = acpi_dp_new_table("_DSD");
|
||||
* acpi_dp_add_integer(dsd, "number1", 1);
|
||||
* acpi_dp_add_gpio(dsd, "gpio", "\_SB.PCI0.GPIO", 0, 0, 1);
|
||||
* acpi_dp_add_child(dsd, "child", child);
|
||||
*
|
||||
* // Write entries into SSDT and clean up resources
|
||||
* acpi_dp_write(dsd);
|
||||
*
|
||||
* Name(_DSD, Package() {
|
||||
* ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301")
|
||||
* Package() {
|
||||
* Package() { "gpio", Package() { \_SB.PCI0.GPIO, 0, 0, 0 } }
|
||||
* Package() { "number1", 1 }
|
||||
* }
|
||||
* ToUUID("dbb8e3e6-5886-4ba6-8795-1319f52a966b")
|
||||
* Package() {
|
||||
* Package() { "child", CHLD }
|
||||
* }
|
||||
* }
|
||||
* Name(CHLD, Package() {
|
||||
* ToUUID("daffd814-6eba-4d8c-8a91-bc9bbf4aa301")
|
||||
* Package() {
|
||||
* Package() { "childstring", "CHILD" }
|
||||
* Package() { "childint", 100 }
|
||||
* }
|
||||
* }
|
||||
*/
|
||||
|
||||
/* Start a new Device Property table with provided ACPI reference */
|
||||
struct acpi_dp *acpi_dp_new_table(const char *ref);
|
||||
|
||||
/* Add integer Device Property */
|
||||
struct acpi_dp *acpi_dp_add_integer(struct acpi_dp *dp, const char *name,
|
||||
uint64_t value);
|
||||
|
||||
/* Add string Device Property */
|
||||
struct acpi_dp *acpi_dp_add_string(struct acpi_dp *dp, const char *name,
|
||||
const char *string);
|
||||
|
||||
/* Add ACPI reference Device Property */
|
||||
struct acpi_dp *acpi_dp_add_reference(struct acpi_dp *dp, const char *name,
|
||||
const char *reference);
|
||||
|
||||
/* Add an array of Device Properties */
|
||||
struct acpi_dp *acpi_dp_add_array(struct acpi_dp *dp, struct acpi_dp *array);
|
||||
|
||||
/* Add an array of integers Device Property */
|
||||
struct acpi_dp *acpi_dp_add_integer_array(struct acpi_dp *dp, const char *name,
|
||||
const uint64_t *array, int len);
|
||||
|
||||
/* Add a GPIO binding Device Property */
|
||||
struct acpi_dp *acpi_dp_add_gpio(struct acpi_dp *dp, const char *name,
|
||||
const char *ref, int index, int pin,
|
||||
int active_low);
|
||||
|
||||
/* Add a child table of Device Properties */
|
||||
struct acpi_dp *acpi_dp_add_child(struct acpi_dp *dp, const char *name,
|
||||
struct acpi_dp *child);
|
||||
|
||||
/* Add a list of Device Properties, returns the number of properties added */
|
||||
size_t acpi_dp_add_property_list(struct acpi_dp *dp,
|
||||
const struct acpi_dp *property_list,
|
||||
size_t property_count);
|
||||
|
||||
/* Write Device Property hierarchy and clean up resources */
|
||||
void acpi_dp_write(struct acpi_dp *table);
|
||||
|
||||
/*
|
||||
* Helper function to write a PCI device with _ADR object defined.
|
||||
*
|
||||
* IMPORTANT: Scope of a device created in SSDT cannot be used to add ACPI nodes under that
|
||||
* scope in DSDT. So, if there are any references to this PCI device scope required from static
|
||||
* asl files, do not use this function and instead add the device to DSDT as well.
|
||||
*/
|
||||
void acpi_device_write_pci_dev(const struct device *dev);
|
||||
|
||||
#endif
|
|
@ -0,0 +1,143 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
/*
|
||||
* AMD I/O Virtualization Technology (IOMMU)
|
||||
* Specification 48882-Rev 2.62-February 2015
|
||||
*
|
||||
* from http://www.uefi.org/acpi
|
||||
* I/O Virtualization Reporting Structure (IVRS)
|
||||
*/
|
||||
|
||||
#ifndef __ARCH_ACPI_IVRS_H
|
||||
#define __ARCH_ACPI_IVRS_H
|
||||
|
||||
/* I/O Virtualization Reporting Structure (IVRS) */
|
||||
#define IVHD_BLOCK_TYPE_LEGACY__FIXED 0x10
|
||||
#define IVHD_BLOCK_TYPE_FULL__FIXED 0x11
|
||||
#define IVHD_BLOCK_TYPE_FULL__ACPI_HID 0x40
|
||||
|
||||
/* IVRS Revision Field */
|
||||
#define IVRS_FORMAT_FIXED 0x01 /* Type 10h & 11h only */
|
||||
#define IVRS_FORMAT_MIXED 0x02 /* Type 10h, 11h, & 40h */
|
||||
|
||||
/* IVRS IVinfo Field */
|
||||
/* ATS response address range reserved */
|
||||
#define IVINFO_HT_ATS_RESERVED (1 << 22)
|
||||
|
||||
/* Virtual Address size - All other values are reserved */
|
||||
#define IVINFO_VA_SIZE_32_BITS (0x20 << 15)
|
||||
#define IVINFO_VA_SIZE_40_BITS (0x28 << 15)
|
||||
#define IVINFO_VA_SIZE_48_BITS (0x30 << 15)
|
||||
#define IVINFO_VA_SIZE_64_BITS (0x40 << 15)
|
||||
|
||||
/* Physical Address size - All other values are reserved */
|
||||
#define IVINFO_PA_SIZE_40_BITS (0x28 << 8)
|
||||
#define IVINFO_PA_SIZE_48_BITS (0x30 << 8)
|
||||
#define IVINFO_PA_SIZE_52_BITS (0x34 << 8)
|
||||
|
||||
/* Guest Virtual Address size - All other values are reserved */
|
||||
#define IVINFO_GVA_SIZE_48_BITS (0x02 << 5)
|
||||
|
||||
/* Extended Feature Support */
|
||||
#define IVINFO_EFR_SUPPORTED 0x01
|
||||
|
||||
/* IVHD Flags Field */
|
||||
#define IVHD_FLAG_PPE_SUP (1 << 7) /* Type 10h only */
|
||||
#define IVHD_FLAG_PREF_SUP (1 << 6) /* Type 10h only */
|
||||
#define IVHD_FLAG_COHERENT (1 << 5)
|
||||
#define IVHD_FLAG_IOTLB_SUP (1 << 4)
|
||||
#define IVHD_FLAG_ISOC (1 << 3)
|
||||
#define IVHD_FLAG_RES_PASS_PW (1 << 2)
|
||||
#define IVHD_FLAG_PASS_PW (1 << 1)
|
||||
#define IVHD_FLAG_HT_TUN_EN (1 << 0)
|
||||
|
||||
/* IVHD IOMMU Info Field */
|
||||
#define IOMMU_INFO_UNIT_ID_SHIFT 8
|
||||
|
||||
/* IVHD IOMMU Feature Reporting Field */
|
||||
#define IOMMU_FEATURE_HATS_SHIFT 30 /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GATS_SHIFT 28 /* Type 10h only */
|
||||
#define IOMMU_FEATURE_MSI_NUM_PPR_SHIFT 23
|
||||
#define IOMMU_FEATURE_PN_BANKS_SHIFT 17
|
||||
#define IOMMU_FEATURE_PN_COUNTERS_SHIFT 13
|
||||
#define IOMMU_FEATURE_PA_SMAX_SHIFT 8 /* Type 10h only */
|
||||
|
||||
#define IOMMU_FEATURE_HE_SUP (1 << 7) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GA_SUP (1 << 6) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_IA_SUP (1 << 5) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GLX_SINGLE_LEVEL (0 << 3) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GLX_TWO_LEVEL (1 << 3) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GLX_THREE_LEVEL (2 << 3) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_GT_SUP (1 << 1) /* Type 10h only */
|
||||
#define IOMMU_FEATURE_NX_SUP (1 << 0) /* Type 10h only */
|
||||
|
||||
/* IVHD Device Entry Type Codes */
|
||||
#define IVHD_DEV_4_BYTE_ALL 0x01
|
||||
#define IVHD_DEV_4_BYTE_SELECT 0x02
|
||||
#define IVHD_DEV_4_BYTE_START_RANGE 0x03
|
||||
#define IVHD_DEV_4_BYTE_END_RANGE 0x04
|
||||
#define IVHD_DEV_8_BYTE_ALIAS_SELECT 0x42
|
||||
#define IVHD_DEV_8_BYTE_ALIAS_START_RANGE 0x43
|
||||
#define IVHD_DEV_8_BYTE_EXT_SELECT 0x46
|
||||
#define IVHD_DEV_8_BYTE_EXT_START_RANGE 0x47
|
||||
#define IVHD_DEV_8_BYTE_EXT_SPECIAL_DEV 0x48
|
||||
#define IVHD_DEV_VARIABLE 0xF0
|
||||
|
||||
/* IVHD Device Table Entry (DTE) Settings */
|
||||
#define IVHD_DTE_LINT_1_PASS (1 << 7)
|
||||
#define IVHD_DTE_LINT_0_PASS (1 << 6)
|
||||
#define IVHD_DTE_SYS_MGT_TGT_ABT (0 << 4)
|
||||
#define IVHD_DTE_SYS_MGT_NO_TRANS (1 << 4)
|
||||
#define IVHD_DTE_SYS_MGT_INTX_NO_TRANS (2 << 4)
|
||||
#define IVHD_DTE_SYS_MGT_TRANS (3 << 4)
|
||||
#define IVHD_DTE_NMI_PASS (1 << 2)
|
||||
#define IVHD_DTE_EXT_INT_PASS (1 << 1)
|
||||
#define IVHD_DTE_INIT_PASS (1 << 0)
|
||||
|
||||
/* IVHD Device Entry Extended DTE Setting Field */
|
||||
#define IVHD_DEV_EXT_ATS_DISABLE (1 << 31)
|
||||
|
||||
/* IVHD Special Device Entry Variety Field */
|
||||
#define IVHD_SPECIAL_DEV_IOAPIC 0x01
|
||||
#define IVHD_SPECIAL_DEV_HPET 0x02
|
||||
|
||||
/* Device EntryType F0h UID Format */
|
||||
#define IVHD_UID_NOT_PRESENT 0x00
|
||||
#define IVHD_UID_INT 0x01
|
||||
#define IVHD_UID_STRING 0x02
|
||||
|
||||
/* IVHD (I/O Virtualization Hardware Definition Block) 4-byte entry */
|
||||
typedef struct ivrs_ivhd_generic {
|
||||
uint8_t type;
|
||||
uint16_t dev_id;
|
||||
uint8_t dte_setting;
|
||||
} __packed ivrs_ivhd_generic_t;
|
||||
|
||||
/* IVHD (I/O Virtualization Hardware Definition Block) 8-byte entries */
|
||||
typedef struct ivrs_ivhd_alias {
|
||||
uint8_t type;
|
||||
uint16_t dev_id;
|
||||
uint8_t dte_setting;
|
||||
uint8_t reserved1;
|
||||
uint16_t source_dev_id;
|
||||
uint8_t reserved2;
|
||||
} __packed ivrs_ivhd_alias_t;
|
||||
|
||||
typedef struct ivrs_ivhd_extended {
|
||||
uint8_t type;
|
||||
uint16_t dev_id;
|
||||
uint8_t dte_setting;
|
||||
uint32_t extended_dte_setting;
|
||||
} __packed ivrs_ivhd_extended_t;
|
||||
|
||||
typedef struct ivrs_ivhd_special {
|
||||
uint8_t type;
|
||||
uint16_t reserved;
|
||||
uint8_t dte_setting;
|
||||
uint8_t handle;
|
||||
uint16_t source_dev_id;
|
||||
uint8_t variety;
|
||||
} __packed ivrs_ivhd_special_t;
|
||||
|
||||
#endif
|
|
@ -0,0 +1,119 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
#ifndef __ACPI_PLD_H
|
||||
#define __ACPI_PLD_H
|
||||
|
||||
#include <arch/acpi.h>
|
||||
#include <stdint.h>
|
||||
|
||||
enum acpi_pld_panel {
|
||||
PLD_PANEL_TOP,
|
||||
PLD_PANEL_BOTTOM,
|
||||
PLD_PANEL_LEFT,
|
||||
PLD_PANEL_RIGHT,
|
||||
PLD_PANEL_FRONT,
|
||||
PLD_PANEL_BACK,
|
||||
PLD_PANEL_UNKNOWN
|
||||
};
|
||||
|
||||
enum acpi_pld_vertical_position {
|
||||
PLD_VERTICAL_POSITION_UPPER,
|
||||
PLD_VERTICAL_POSITION_CENTER,
|
||||
PLD_VERTICAL_POSITION_LOWER
|
||||
};
|
||||
|
||||
/*
|
||||
* The ACPI spec 6.2A does not define the horizontal position field.
|
||||
* These values are taken from the IASL compiler:
|
||||
* https://github.com/acpica/acpica/blob/master/source/components/utilities/utglobal.c#L321
|
||||
*/
|
||||
|
||||
enum acpi_pld_horizontal_position {
|
||||
PLD_HORIZONTAL_POSITION_LEFT,
|
||||
PLD_HORIZONTAL_POSITION_CENTER,
|
||||
PLD_HORIZONTAL_POSITION_RIGHT
|
||||
};
|
||||
|
||||
enum acpi_pld_shape {
|
||||
PLD_SHAPE_ROUND,
|
||||
PLD_SHAPE_OVAL,
|
||||
PLD_SHAPE_SQUARE,
|
||||
PLD_SHAPE_VERTICAL_RECTANGLE,
|
||||
PLD_SHAPE_HORIZONTAL_RECTANGLE,
|
||||
PLD_SHAPE_VERTICAL_TRAPEZOID,
|
||||
PLD_SHAPE_HORIZONTAL_TRAPEZOID,
|
||||
PLD_SHAPE_UNKNOWN,
|
||||
PLD_SHAPE_CHAMFERED
|
||||
};
|
||||
|
||||
enum acpi_pld_orientation {
|
||||
PLD_ORIENTATION_HORIZONTAL,
|
||||
PLD_ORIENTATION_VERTICAL,
|
||||
};
|
||||
|
||||
enum acpi_pld_rotate {
|
||||
PLD_ROTATE_0,
|
||||
PLD_ROTATE_45,
|
||||
PLD_ROTATE_90,
|
||||
PLD_ROTATE_135,
|
||||
PLD_ROTATE_180,
|
||||
PLD_ROTATE_225,
|
||||
PLD_ROTATE_270,
|
||||
PLD_ROTATE_315
|
||||
};
|
||||
|
||||
#define ACPI_PLD_GROUP(__token, __position) \
|
||||
{ \
|
||||
.token = __token, \
|
||||
.position = __position, \
|
||||
}
|
||||
|
||||
struct acpi_pld_group {
|
||||
uint8_t token;
|
||||
uint8_t position;
|
||||
};
|
||||
|
||||
struct acpi_pld {
|
||||
/* Color field can be explicitly ignored */
|
||||
bool ignore_color;
|
||||
uint8_t color_red;
|
||||
uint8_t color_blue;
|
||||
uint8_t color_green;
|
||||
|
||||
/* Port characteristics */
|
||||
bool visible; /* Can be seen by the user */
|
||||
bool lid; /* Port is on lid of device */
|
||||
bool dock; /* Port is in a docking station */
|
||||
bool bay; /* Port is in a bay */
|
||||
bool ejectable; /* Device is ejectable, has _EJx objects */
|
||||
bool ejectable_ospm; /* Device needs OSPM to eject */
|
||||
uint16_t width; /* Width in mm */
|
||||
uint16_t height; /* Height in mm */
|
||||
uint16_t vertical_offset;
|
||||
uint16_t horizontal_offset;
|
||||
enum acpi_pld_panel panel;
|
||||
enum acpi_pld_horizontal_position horizontal_position;
|
||||
enum acpi_pld_vertical_position vertical_position;
|
||||
enum acpi_pld_shape shape;
|
||||
enum acpi_pld_rotate rotation;
|
||||
|
||||
/* Port grouping */
|
||||
enum acpi_pld_orientation orientation;
|
||||
struct acpi_pld_group group;
|
||||
uint8_t draw_order;
|
||||
uint8_t cabinet_number;
|
||||
uint8_t card_cage_number;
|
||||
|
||||
/* Set if this PLD defines a reference shape */
|
||||
bool reference_shape;
|
||||
};
|
||||
|
||||
/* Fill out PLD structure with defaults based on USB port type */
|
||||
int acpi_pld_fill_usb(struct acpi_pld *pld, enum acpi_upc_type type,
|
||||
struct acpi_pld_group *group);
|
||||
|
||||
/* Turn PLD structure into a 20 byte ACPI buffer */
|
||||
int acpi_pld_to_buffer(const struct acpi_pld *pld, uint8_t *buf, int buf_len);
|
||||
|
||||
#endif
|
|
@ -0,0 +1,490 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
#ifndef LIBACPI_H
|
||||
#define LIBACPI_H
|
||||
|
||||
#include <stdint.h>
|
||||
#include <arch/acpi.h>
|
||||
#include <arch/acpi_device.h>
|
||||
#include <arch/acpi_pld.h>
|
||||
#include <device/pci_type.h>
|
||||
|
||||
/* Values that can be returned for ACPI Device _STA method */
|
||||
#define ACPI_STATUS_DEVICE_PRESENT (1 << 0)
|
||||
#define ACPI_STATUS_DEVICE_ENABLED (1 << 1)
|
||||
#define ACPI_STATUS_DEVICE_SHOW_IN_UI (1 << 2)
|
||||
#define ACPI_STATUS_DEVICE_STATE_OK (1 << 3)
|
||||
|
||||
#define ACPI_STATUS_DEVICE_ALL_OFF 0
|
||||
#define ACPI_STATUS_DEVICE_ALL_ON (ACPI_STATUS_DEVICE_PRESENT |\
|
||||
ACPI_STATUS_DEVICE_ENABLED |\
|
||||
ACPI_STATUS_DEVICE_SHOW_IN_UI |\
|
||||
ACPI_STATUS_DEVICE_STATE_OK)
|
||||
#define ACPI_STATUS_DEVICE_HIDDEN_ON (ACPI_STATUS_DEVICE_PRESENT |\
|
||||
ACPI_STATUS_DEVICE_ENABLED |\
|
||||
ACPI_STATUS_DEVICE_STATE_OK)
|
||||
|
||||
/* ACPI Op/Prefix Codes */
|
||||
enum {
|
||||
ZERO_OP = 0x00,
|
||||
ONE_OP = 0x01,
|
||||
ALIAS_OP = 0x06,
|
||||
NAME_OP = 0x08,
|
||||
BYTE_PREFIX = 0x0A,
|
||||
WORD_PREFIX = 0x0B,
|
||||
DWORD_PREFIX = 0x0C,
|
||||
STRING_PREFIX = 0x0D,
|
||||
QWORD_PREFIX = 0x0E,
|
||||
SCOPE_OP = 0x10,
|
||||
BUFFER_OP = 0x11,
|
||||
PACKAGE_OP = 0x12,
|
||||
VARIABLE_PACKAGE_OP = 0x13,
|
||||
METHOD_OP = 0x14,
|
||||
EXTERNAL_OP = 0x15,
|
||||
DUAL_NAME_PREFIX = 0x2E,
|
||||
MULTI_NAME_PREFIX = 0x2F,
|
||||
EXT_OP_PREFIX = 0x5B,
|
||||
MUTEX_OP = 0x01,
|
||||
EVENT_OP = 0x01,
|
||||
SF_RIGHT_OP = 0x10,
|
||||
SF_LEFT_OP = 0x11,
|
||||
COND_REFOF_OP = 0x12,
|
||||
CREATEFIELD_OP = 0x13,
|
||||
LOAD_TABLE_OP = 0x1f,
|
||||
LOAD_OP = 0x20,
|
||||
STALL_OP = 0x21,
|
||||
SLEEP_OP = 0x22,
|
||||
ACQUIRE_OP = 0x23,
|
||||
SIGNAL_OP = 0x24,
|
||||
WAIT_OP = 0x25,
|
||||
RST_OP = 0x26,
|
||||
RELEASE_OP = 0x27,
|
||||
FROM_BCD_OP = 0x28,
|
||||
TO_BCD_OP = 0x29,
|
||||
UNLOAD_OP = 0x2A,
|
||||
REVISON_OP = 0x30,
|
||||
DEBUG_OP = 0x31,
|
||||
FATAL_OP = 0x32,
|
||||
TIMER_OP = 0x33,
|
||||
OPREGION_OP = 0x80,
|
||||
FIELD_OP = 0x81,
|
||||
DEVICE_OP = 0x82,
|
||||
PROCESSOR_OP = 0x83,
|
||||
POWER_RES_OP = 0x84,
|
||||
THERMAL_ZONE_OP = 0x85,
|
||||
INDEX_FIELD_OP = 0x86,
|
||||
BANK_FIELD_OP = 0x87,
|
||||
DATA_REGION_OP = 0x88,
|
||||
ROOT_PREFIX = 0x5C,
|
||||
PARENT_PREFIX = 0x5E,
|
||||
LOCAL0_OP = 0x60,
|
||||
LOCAL1_OP = 0x61,
|
||||
LOCAL2_OP = 0x62,
|
||||
LOCAL3_OP = 0x63,
|
||||
LOCAL4_OP = 0x64,
|
||||
LOCAL5_OP = 0x65,
|
||||
LOCAL6_OP = 0x66,
|
||||
LOCAL7_OP = 0x67,
|
||||
ARG0_OP = 0x68,
|
||||
ARG1_OP = 0x69,
|
||||
ARG2_OP = 0x6A,
|
||||
ARG3_OP = 0x6B,
|
||||
ARG4_OP = 0x6C,
|
||||
ARG5_OP = 0x6D,
|
||||
ARG6_OP = 0x6E,
|
||||
STORE_OP = 0x70,
|
||||
REF_OF_OP = 0x71,
|
||||
ADD_OP = 0x72,
|
||||
CONCATENATE_OP = 0x73,
|
||||
SUBTRACT_OP = 0x74,
|
||||
INCREMENT_OP = 0x75,
|
||||
DECREMENT_OP = 0x76,
|
||||
MULTIPLY_OP = 0x77,
|
||||
DIVIDE_OP = 0x78,
|
||||
SHIFT_LEFT_OP = 0x79,
|
||||
SHIFT_RIGHT_OP = 0x7A,
|
||||
AND_OP = 0x7B,
|
||||
NAND_OP = 0x7C,
|
||||
OR_OP = 0x7D,
|
||||
NOR_OP = 0x7E,
|
||||
XOR_OP = 0x7F,
|
||||
NOT_OP = 0x80,
|
||||
FD_SHIFT_LEFT_BIT_OR = 0x81,
|
||||
FD_SHIFT_RIGHT_BIT_OR = 0x82,
|
||||
DEREF_OP = 0x83,
|
||||
CONCATENATE_TEMP_OP = 0x84,
|
||||
MOD_OP = 0x85,
|
||||
NOTIFY_OP = 0x86,
|
||||
SIZEOF_OP = 0x87,
|
||||
INDEX_OP = 0x88,
|
||||
MATCH_OP = 0x89,
|
||||
CREATE_DWORD_OP = 0x8A,
|
||||
CREATE_WORD_OP = 0x8B,
|
||||
CREATE_BYTE_OP = 0x8C,
|
||||
CREATE_BIT_OP = 0x8D,
|
||||
OBJ_TYPE_OP = 0x8E,
|
||||
CREATE_QWORD_OP = 0x8F,
|
||||
LAND_OP = 0x90,
|
||||
LOR_OP = 0x91,
|
||||
LNOT_OP = 0x92,
|
||||
LEQUAL_OP = 0x93,
|
||||
LGREATER_OP = 0x94,
|
||||
LLESS_OP = 0x95,
|
||||
TO_BUFFER_OP = 0x96,
|
||||
TO_DEC_STRING_OP = 0x97,
|
||||
TO_HEX_STRING_OP = 0x98,
|
||||
TO_INTEGER_OP = 0x99,
|
||||
TO_STRING_OP = 0x9C,
|
||||
CP_OBJ_OP = 0x9D,
|
||||
MID_OP = 0x9E,
|
||||
CONTINUE_OP = 0x9F,
|
||||
IF_OP = 0xA0,
|
||||
ELSE_OP = 0xA1,
|
||||
WHILE_OP = 0xA2,
|
||||
NOOP_OP = 0xA3,
|
||||
RETURN_OP = 0xA4,
|
||||
BREAK_OP = 0xA5,
|
||||
COMMENT_OP = 0xA9,
|
||||
BREAKPIONT_OP = 0xCC,
|
||||
ONES_OP = 0xFF,
|
||||
};
|
||||
|
||||
#define FIELDLIST_OFFSET(X) { .type = OFFSET, \
|
||||
.name = "",\
|
||||
.bits = X * 8, \
|
||||
}
|
||||
#define FIELDLIST_NAMESTR(X, Y) { .type = NAME_STRING, \
|
||||
.name = X, \
|
||||
.bits = Y, \
|
||||
}
|
||||
|
||||
#define FIELD_ANYACC 0
|
||||
#define FIELD_BYTEACC 1
|
||||
#define FIELD_WORDACC 2
|
||||
#define FIELD_DWORDACC 3
|
||||
#define FIELD_QWORDACC 4
|
||||
#define FIELD_BUFFERACC 5
|
||||
#define FIELD_NOLOCK (0<<4)
|
||||
#define FIELD_LOCK (1<<4)
|
||||
#define FIELD_PRESERVE (0<<5)
|
||||
#define FIELD_WRITEASONES (1<<5)
|
||||
#define FIELD_WRITEASZEROS (2<<5)
|
||||
|
||||
enum field_type {
|
||||
OFFSET,
|
||||
NAME_STRING,
|
||||
FIELD_TYPE_MAX,
|
||||
};
|
||||
|
||||
struct fieldlist {
|
||||
enum field_type type;
|
||||
const char *name;
|
||||
u32 bits;
|
||||
};
|
||||
|
||||
#define OPREGION(rname, space, offset, len) {.name = rname, \
|
||||
.regionspace = space, \
|
||||
.regionoffset = offset, \
|
||||
.regionlen = len, \
|
||||
}
|
||||
|
||||
enum region_space {
|
||||
SYSTEMMEMORY,
|
||||
SYSTEMIO,
|
||||
PCI_CONFIG,
|
||||
EMBEDDEDCONTROL,
|
||||
SMBUS,
|
||||
CMOS,
|
||||
PCIBARTARGET,
|
||||
IPMI,
|
||||
GPIO_REGION,
|
||||
GPSERIALBUS,
|
||||
PCC,
|
||||
FIXED_HARDWARE = 0x7F,
|
||||
REGION_SPACE_MAX,
|
||||
};
|
||||
|
||||
struct opregion {
|
||||
const char *name;
|
||||
enum region_space regionspace;
|
||||
unsigned long regionoffset;
|
||||
unsigned long regionlen;
|
||||
};
|
||||
|
||||
#define DSM_UUID(DSM_UUID, DSM_CALLBACKS, DSM_COUNT, DSM_ARG) \
|
||||
{ .uuid = DSM_UUID, \
|
||||
.callbacks = DSM_CALLBACKS, \
|
||||
.count = DSM_COUNT, \
|
||||
.arg = DSM_ARG, \
|
||||
}
|
||||
|
||||
struct dsm_uuid {
|
||||
const char *uuid;
|
||||
void (**callbacks)(void *);
|
||||
size_t count;
|
||||
void *arg;
|
||||
};
|
||||
|
||||
/*version 1 has 15 fields, version 2 has 19, and version 3 has 21 */
|
||||
enum cppc_fields {
|
||||
CPPC_HIGHEST_PERF, /* can be DWORD */
|
||||
CPPC_NOMINAL_PERF, /* can be DWORD */
|
||||
CPPC_LOWEST_NONL_PERF, /* can be DWORD */
|
||||
CPPC_LOWEST_PERF, /* can be DWORD */
|
||||
CPPC_GUARANTEED_PERF,
|
||||
CPPC_DESIRED_PERF,
|
||||
CPPC_MIN_PERF,
|
||||
CPPC_MAX_PERF,
|
||||
CPPC_PERF_REDUCE_TOLERANCE,
|
||||
CPPC_TIME_WINDOW,
|
||||
CPPC_COUNTER_WRAP, /* can be DWORD */
|
||||
CPPC_REF_PERF_COUNTER,
|
||||
CPPC_DELIVERED_PERF_COUNTER,
|
||||
CPPC_PERF_LIMITED,
|
||||
CPPC_ENABLE, /* can be System I/O */
|
||||
CPPC_MAX_FIELDS_VER_1,
|
||||
CPPC_AUTO_SELECT = /* can be DWORD */
|
||||
CPPC_MAX_FIELDS_VER_1,
|
||||
CPPC_AUTO_ACTIVITY_WINDOW,
|
||||
CPPC_PERF_PREF,
|
||||
CPPC_REF_PERF, /* can be DWORD */
|
||||
CPPC_MAX_FIELDS_VER_2,
|
||||
CPPC_LOWEST_FREQ = /* can be DWORD */
|
||||
CPPC_MAX_FIELDS_VER_2,
|
||||
CPPC_NOMINAL_FREQ, /* can be DWORD */
|
||||
CPPC_MAX_FIELDS_VER_3,
|
||||
};
|
||||
|
||||
struct cppc_config {
|
||||
u32 version; /* must be 1, 2, or 3 */
|
||||
/*
|
||||
* The generic acpi_addr_t structure is being used, though
|
||||
* anything besides PPC or FFIXED generally requires checking
|
||||
* if the OS has advertised support for it (via _OSC).
|
||||
*
|
||||
* NOTE: some fields permit DWORDs to be used. If you
|
||||
* provide a System Memory register with all zeros (which
|
||||
* represents unsupported) then this will be used as-is.
|
||||
* Otherwise, a System Memory register with a 32-bit
|
||||
* width will be converted into a DWORD field (the value
|
||||
* of which will be the value of 'addrl'. Any other use
|
||||
* of System Memory register is currently undefined.
|
||||
* (i.e., if you have an actual need for System Memory
|
||||
* then you'll need to adjust this kludge).
|
||||
*/
|
||||
acpi_addr_t regs[CPPC_MAX_FIELDS_VER_3];
|
||||
};
|
||||
|
||||
void acpigen_write_return_integer(uint64_t arg);
|
||||
void acpigen_write_return_string(const char *arg);
|
||||
void acpigen_write_len_f(void);
|
||||
void acpigen_pop_len(void);
|
||||
void acpigen_set_current(char *curr);
|
||||
char *acpigen_get_current(void);
|
||||
char *acpigen_write_package(int nr_el);
|
||||
void acpigen_write_zero(void);
|
||||
void acpigen_write_one(void);
|
||||
void acpigen_write_ones(void);
|
||||
void acpigen_write_byte(unsigned int data);
|
||||
void acpigen_emit_byte(unsigned char data);
|
||||
void acpigen_emit_ext_op(uint8_t op);
|
||||
void acpigen_emit_word(unsigned int data);
|
||||
void acpigen_emit_dword(unsigned int data);
|
||||
void acpigen_emit_stream(const char *data, int size);
|
||||
void acpigen_emit_string(const char *string);
|
||||
void acpigen_emit_namestring(const char *namepath);
|
||||
void acpigen_emit_eisaid(const char *eisaid);
|
||||
void acpigen_write_word(unsigned int data);
|
||||
void acpigen_write_dword(unsigned int data);
|
||||
void acpigen_write_qword(uint64_t data);
|
||||
void acpigen_write_integer(uint64_t data);
|
||||
void acpigen_write_string(const char *string);
|
||||
void acpigen_write_name_unicode(const char *name, const char *string);
|
||||
void acpigen_write_name(const char *name);
|
||||
void acpigen_write_name_zero(const char *name);
|
||||
void acpigen_write_name_one(const char *name);
|
||||
void acpigen_write_name_string(const char *name, const char *string);
|
||||
void acpigen_write_name_dword(const char *name, uint32_t val);
|
||||
void acpigen_write_name_qword(const char *name, uint64_t val);
|
||||
void acpigen_write_name_byte(const char *name, uint8_t val);
|
||||
void acpigen_write_name_integer(const char *name, uint64_t val);
|
||||
void acpigen_write_coreboot_hid(enum coreboot_acpi_ids id);
|
||||
void acpigen_write_scope(const char *name);
|
||||
void acpigen_write_method(const char *name, int nargs);
|
||||
void acpigen_write_method_serialized(const char *name, int nargs);
|
||||
void acpigen_write_device(const char *name);
|
||||
void acpigen_write_PPC(u8 nr);
|
||||
void acpigen_write_PPC_NVS(void);
|
||||
void acpigen_write_empty_PCT(void);
|
||||
void acpigen_write_empty_PTC(void);
|
||||
void acpigen_write_PRW(u32 wake, u32 level);
|
||||
void acpigen_write_STA(uint8_t status);
|
||||
void acpigen_write_TPC(const char *gnvs_tpc_limit);
|
||||
void acpigen_write_PSS_package(u32 coreFreq, u32 power, u32 transLat,
|
||||
u32 busmLat, u32 control, u32 status);
|
||||
typedef enum { SW_ALL = 0xfc, SW_ANY = 0xfd, HW_ALL = 0xfe } PSD_coord;
|
||||
void acpigen_write_PSD_package(u32 domain, u32 numprocs, PSD_coord coordtype);
|
||||
void acpigen_write_CST_package_entry(acpi_cstate_t *cstate);
|
||||
void acpigen_write_CST_package(acpi_cstate_t *entry, int nentries);
|
||||
typedef enum { CSD_HW_ALL = 0xfe } CSD_coord;
|
||||
void acpigen_write_CSD_package(u32 domain, u32 numprocs, CSD_coord coordtype,
|
||||
u32 index);
|
||||
void acpigen_write_processor(u8 cpuindex, u32 pblock_addr, u8 pblock_len);
|
||||
void acpigen_write_processor_package(const char *name,
|
||||
unsigned int first_core,
|
||||
unsigned int core_count);
|
||||
void acpigen_write_processor_cnot(const unsigned int number_of_cores);
|
||||
void acpigen_write_TSS_package(int entries, acpi_tstate_t *tstate_list);
|
||||
void acpigen_write_TSD_package(u32 domain, u32 numprocs, PSD_coord coordtype);
|
||||
void acpigen_write_mem32fixed(int readwrite, u32 base, u32 size);
|
||||
void acpigen_write_io16(u16 min, u16 max, u8 align, u8 len, u8 decode16);
|
||||
void acpigen_write_register_resource(const acpi_addr_t *addr);
|
||||
void acpigen_write_resourcetemplate_header(void);
|
||||
void acpigen_write_resourcetemplate_footer(void);
|
||||
void acpigen_write_mainboard_resource_template(void);
|
||||
void acpigen_write_mainboard_resources(const char *scope, const char *name);
|
||||
void acpigen_write_irq(u16 mask);
|
||||
void acpigen_write_uuid(const char *uuid);
|
||||
void acpigen_write_power_res(const char *name, uint8_t level, uint16_t order,
|
||||
const char * const dev_states[], size_t dev_states_count);
|
||||
void acpigen_write_sleep(uint64_t sleep_ms);
|
||||
void acpigen_write_store(void);
|
||||
void acpigen_write_store_ops(uint8_t src, uint8_t dst);
|
||||
void acpigen_write_store_op_to_namestr(uint8_t src, const char *dst);
|
||||
void acpigen_write_or(uint8_t arg1, uint8_t arg2, uint8_t res);
|
||||
void acpigen_write_xor(uint8_t arg1, uint8_t arg2, uint8_t res);
|
||||
void acpigen_write_and(uint8_t arg1, uint8_t arg2, uint8_t res);
|
||||
void acpigen_write_not(uint8_t arg, uint8_t res);
|
||||
void acpigen_write_debug_string(const char *str);
|
||||
void acpigen_write_debug_integer(uint64_t val);
|
||||
void acpigen_write_debug_op(uint8_t op);
|
||||
void acpigen_write_if(void);
|
||||
void acpigen_write_if_and(uint8_t arg1, uint8_t arg2);
|
||||
void acpigen_write_if_lequal_op_int(uint8_t op, uint64_t val);
|
||||
void acpigen_write_if_lequal_namestr_int(const char *namestr, uint64_t val);
|
||||
void acpigen_write_else(void);
|
||||
void acpigen_write_to_buffer(uint8_t src, uint8_t dst);
|
||||
void acpigen_write_to_integer(uint8_t src, uint8_t dst);
|
||||
void acpigen_write_byte_buffer(uint8_t *arr, size_t size);
|
||||
void acpigen_write_return_byte_buffer(uint8_t *arr, size_t size);
|
||||
void acpigen_write_return_singleton_buffer(uint8_t arg);
|
||||
void acpigen_write_return_byte(uint8_t arg);
|
||||
void acpigen_write_upc(enum acpi_upc_type type);
|
||||
void acpigen_write_pld(const struct acpi_pld *pld);
|
||||
void acpigen_write_ADR(uint64_t adr);
|
||||
void acpigen_write_ADR_pci_devfn(pci_devfn_t devfn);
|
||||
void acpigen_write_ADR_pci_device(const struct device *dev);
|
||||
/*
|
||||
* Generate ACPI AML code for _DSM method.
|
||||
* This function takes as input uuid for the device, set of callbacks and
|
||||
* argument to pass into the callbacks. Callbacks should ensure that Local0 and
|
||||
* Local1 are left untouched. Use of Local2-Local7 is permitted in callbacks.
|
||||
*/
|
||||
void acpigen_write_dsm(const char *uuid, void (**callbacks)(void *),
|
||||
size_t count, void *arg);
|
||||
void acpigen_write_dsm_uuid_arr(struct dsm_uuid *ids, size_t count);
|
||||
|
||||
/*
|
||||
* Generate ACPI AML code for _CPC (Continuous Performance Control).
|
||||
* Execute the package function once to create a global table, then
|
||||
* execute the method function within each processor object to
|
||||
* create a method that points to the global table.
|
||||
*/
|
||||
void acpigen_write_CPPC_package(const struct cppc_config *config);
|
||||
void acpigen_write_CPPC_method(void);
|
||||
|
||||
/*
|
||||
* Generate ACPI AML code for _ROM method.
|
||||
* This function takes as input ROM data and ROM length.
|
||||
* The ROM length has to be multiple of 4096 and has to be less
|
||||
* than the current implementation limit of 0x40000.
|
||||
*/
|
||||
void acpigen_write_rom(void *bios, const size_t length);
|
||||
/*
|
||||
* Generate ACPI AML code for OperationRegion
|
||||
* This function takes input region name, region space, region offset & region
|
||||
* length.
|
||||
*/
|
||||
void acpigen_write_opregion(struct opregion *opreg);
|
||||
/*
|
||||
* Generate ACPI AML code for Mutex
|
||||
* This function takes mutex name and initial value.
|
||||
*/
|
||||
void acpigen_write_mutex(const char *name, const uint8_t flags);
|
||||
/*
|
||||
* Generate ACPI AML code for Acquire
|
||||
* This function takes mutex name and privilege value.
|
||||
*/
|
||||
void acpigen_write_acquire(const char *name, const uint16_t val);
|
||||
/*
|
||||
* Generate ACPI AML code for Release
|
||||
* This function takes mutex name.
|
||||
*/
|
||||
void acpigen_write_release(const char *name);
|
||||
/*
|
||||
* Generate ACPI AML code for Field
|
||||
* This function takes input region name, fieldlist, count & flags.
|
||||
*/
|
||||
void acpigen_write_field(const char *name, const struct fieldlist *l, size_t count,
|
||||
uint8_t flags);
|
||||
/*
|
||||
* Generate ACPI AML code for IndexField
|
||||
* This function takes input index name, data name, fieldlist, count & flags.
|
||||
*/
|
||||
void acpigen_write_indexfield(const char *idx, const char *data,
|
||||
struct fieldlist *l, size_t count, uint8_t flags);
|
||||
|
||||
int get_cst_entries(acpi_cstate_t **);
|
||||
|
||||
/*
|
||||
* Soc-implemented functions for generating ACPI AML code for GPIO handling. All
|
||||
* these functions are expected to use only Local5, Local6 and Local7
|
||||
* variables. If the functions call into another ACPI method, then there is no
|
||||
* restriction on the use of Local variables. In case of get/read functions,
|
||||
* return value is expected to be stored in Local0 variable.
|
||||
*
|
||||
* All functions return 0 on success and -1 on error.
|
||||
*/
|
||||
|
||||
/* Generate ACPI AML code to return Rx value of GPIO in Local0. */
|
||||
int acpigen_soc_read_rx_gpio(unsigned int gpio_num);
|
||||
|
||||
/* Generate ACPI AML code to return Tx value of GPIO in Local0. */
|
||||
int acpigen_soc_get_tx_gpio(unsigned int gpio_num);
|
||||
|
||||
/* Generate ACPI AML code to set Tx value of GPIO to 1. */
|
||||
int acpigen_soc_set_tx_gpio(unsigned int gpio_num);
|
||||
|
||||
/* Generate ACPI AML code to set Tx value of GPIO to 0. */
|
||||
int acpigen_soc_clear_tx_gpio(unsigned int gpio_num);
|
||||
|
||||
/*
|
||||
* Helper functions for enabling/disabling Tx GPIOs based on the GPIO
|
||||
* polarity. These functions end up calling acpigen_soc_{set,clear}_tx_gpio to
|
||||
* make callbacks into SoC acpigen code.
|
||||
*
|
||||
* Returns 0 on success and -1 on error.
|
||||
*/
|
||||
int acpigen_enable_tx_gpio(struct acpi_gpio *gpio);
|
||||
int acpigen_disable_tx_gpio(struct acpi_gpio *gpio);
|
||||
|
||||
/*
|
||||
* Helper function for getting a RX GPIO value based on the GPIO polarity.
|
||||
* The return value is stored in Local0 variable.
|
||||
* This function ends up calling acpigen_soc_get_rx_gpio to make callbacks
|
||||
* into SoC acpigen code
|
||||
*/
|
||||
void acpigen_get_rx_gpio(struct acpi_gpio *gpio);
|
||||
|
||||
/* refer to ACPI 6.4.3.5.3 Word Address Space Descriptor section for details */
|
||||
void acpigen_resource_word(u16 res_type, u16 gen_flags, u16 type_flags, u16 gran,
|
||||
u16 range_min, u16 range_max, u16 translation, u16 length);
|
||||
/* refer to ACPI 6.4.3.5.2 DWord Address Space Descriptor section for details */
|
||||
void acpigen_resource_dword(u16 res_type, u16 gen_flags, u16 type_flags,
|
||||
u32 gran, u32 range_min, u32 range_max, u32 translation, u32 length);
|
||||
/* refer to ACPI 6.4.3.5.1 QWord Address Space Descriptor section for details */
|
||||
void acpigen_resource_qword(u16 res_type, u16 gen_flags, u16 type_flags,
|
||||
u64 gran, u64 range_min, u64 range_max, u64 translation, u64 length);
|
||||
|
||||
#endif
|
|
@ -0,0 +1,15 @@
|
|||
/* SPDX-License-Identifier: GPL-2.0-only */
|
||||
/* This file is part of the coreboot project. */
|
||||
|
||||
#ifndef __ARCH_ACPIGEN_DSM_H__
|
||||
#define __ARCH_ACPIGEN_DSM_H__
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
struct dsm_i2c_hid_config {
|
||||
uint8_t hid_desc_reg_offset;
|
||||
};
|
||||
|
||||
void acpigen_write_dsm_i2c_hid(struct dsm_i2c_hid_config *config);
|
||||
|
||||
#endif /* __ARCH_ACPIGEN_DSM_H__ */
|
|
@ -0,0 +1,41 @@
|
|||
/*
|
||||
* This file is part of the coreboot project.
|
||||
*
|
||||
* SPDX-License-Identifier: GPL-2.0-or-later
|
||||
*/
|
||||
|
||||
#ifndef __ACPIGEN_PS2_KEYBD_H__
|
||||
#define __ACPIGEN_PS2_KEYBD_H__
|
||||
|
||||
#include <types.h>
|
||||
|
||||
enum ps2_action_key {
|
||||
PS2_KEY_ABSENT = 0,
|
||||
PS2_KEY_BACK,
|
||||
PS2_KEY_FORWARD,
|
||||
PS2_KEY_REFRESH,
|
||||
PS2_KEY_FULLSCREEN,
|
||||
PS2_KEY_OVERVIEW,
|
||||
PS2_KEY_BRIGHTNESS_DOWN,
|
||||
PS2_KEY_BRIGHTNESS_UP,
|
||||
PS2_KEY_VOL_MUTE,
|
||||
PS2_KEY_VOL_DOWN,
|
||||
PS2_KEY_VOL_UP,
|
||||
PS2_KEY_SNAPSHOT,
|
||||
PS2_KEY_PRIVACY_SCRN_TOGGLE,
|
||||
PS2_KEY_KBD_BKLIGHT_DOWN,
|
||||
PS2_KEY_KBD_BKLIGHT_UP,
|
||||
PS2_KEY_PLAY_PAUSE,
|
||||
PS2_KEY_NEXT_TRACK,
|
||||
PS2_KEY_PREV_TRACK,
|
||||
};
|
||||
|
||||
#define PS2_MIN_TOP_ROW_KEYS 10
|
||||
#define PS2_MAX_TOP_ROW_KEYS 15
|
||||
|
||||
void acpigen_ps2_keyboard_dsd(const char *scope, uint8_t num_top_row_keys,
|
||||
enum ps2_action_key action_keys[],
|
||||
bool can_send_function_keys,
|
||||
bool has_numeric_keypad, bool has_scrnlock_key);
|
||||
|
||||
#endif /* __ACPIGEN_PS2_KEYBD_H__ */
|
Loading…
Reference in New Issue