summaryrefslogtreecommitdiff
path: root/src/ec/google/wilco/chip.c
diff options
context:
space:
mode:
authorDuncan Laurie <dlaurie@google.com>2019-04-18 16:37:50 -0700
committerDuncan Laurie <dlaurie@chromium.org>2019-06-07 20:51:16 +0000
commitc145e54f695480ac02f752a6d01e98cb37248a07 (patch)
treec60ba05b1ee70085fc6f8c9f5278e6f5d48c3d78 /src/ec/google/wilco/chip.c
parentc1c60601eeba69b1a897fec59e00f2dcc65f90dd (diff)
ec/google/wilco: Add UCSI support
This change adds support for the UCSI specification in order to provide information about the Type-C port and an interface to perform power and data role swap. This change is split across the DSDT and SSDT, with the shared memory and operation region declared in the SSDT after being allocated in CBMEM. The OS will fill in the registers in the system memory region and then call the _DSM method wtih a read or write argument. The DSM method will copy the required registers to/from the system memory and the EC and perform the write or read action. Responses from the EC will generate a new SCI with event code 0x79 which will notify this UCSI ACPI device and the OS driver will take action to read status from the EC. BUG=b:131083691 Change-Id: I438a2bdfaf6720acd8354e0339dcef2844b63a4e Signed-off-by: Duncan Laurie <dlaurie@google.com> Reviewed-on: https://review.coreboot.org/c/coreboot/+/32357 Tested-by: build bot (Jenkins) <no-reply@coreboot.org> Reviewed-by: Furquan Shaikh <furquan@google.com>
Diffstat (limited to 'src/ec/google/wilco/chip.c')
-rw-r--r--src/ec/google/wilco/chip.c105
1 files changed, 101 insertions, 4 deletions
diff --git a/src/ec/google/wilco/chip.c b/src/ec/google/wilco/chip.c
index 9b0be19f9a..09211f82ab 100644
--- a/src/ec/google/wilco/chip.c
+++ b/src/ec/google/wilco/chip.c
@@ -14,7 +14,10 @@
*/
#include <arch/acpi.h>
+#include <arch/acpi_device.h>
+#include <arch/acpigen.h>
#include <bootstate.h>
+#include <cbmem.h>
#include <device/pnp.h>
#include <ec/acpi/ec.h>
#include <pc80/keyboard.h>
@@ -25,6 +28,64 @@
#include "ec.h"
#include "chip.h"
+/*
+ * The UCSI fields are defined in the UCSI specification at
+ * https://www.intel.com/content/www/us/en/io/universal-serial-bus/usb-type-c-ucsi-spec.html
+ * https://www.intel.com/content/www/us/en/io/universal-serial-bus/bios-implementation-of-ucsi.html
+ */
+
+static struct fieldlist ucsi_region_fields[] = {
+ FIELDLIST_NAMESTR("VER0", 8),
+ FIELDLIST_NAMESTR("VER1", 8),
+ FIELDLIST_NAMESTR("RSV0", 8),
+ FIELDLIST_NAMESTR("RSV1", 8),
+ FIELDLIST_NAMESTR("CCI0", 8),
+ FIELDLIST_NAMESTR("CCI1", 8),
+ FIELDLIST_NAMESTR("CCI2", 8),
+ FIELDLIST_NAMESTR("CCI3", 8),
+ FIELDLIST_NAMESTR("CTL0", 8),
+ FIELDLIST_NAMESTR("CTL1", 8),
+ FIELDLIST_NAMESTR("CTL2", 8),
+ FIELDLIST_NAMESTR("CTL3", 8),
+ FIELDLIST_NAMESTR("CTL4", 8),
+ FIELDLIST_NAMESTR("CTL5", 8),
+ FIELDLIST_NAMESTR("CTL6", 8),
+ FIELDLIST_NAMESTR("CTL7", 8),
+ FIELDLIST_NAMESTR("MGI0", 8),
+ FIELDLIST_NAMESTR("MGI1", 8),
+ FIELDLIST_NAMESTR("MGI2", 8),
+ FIELDLIST_NAMESTR("MGI3", 8),
+ FIELDLIST_NAMESTR("MGI4", 8),
+ FIELDLIST_NAMESTR("MGI5", 8),
+ FIELDLIST_NAMESTR("MGI6", 8),
+ FIELDLIST_NAMESTR("MGI7", 8),
+ FIELDLIST_NAMESTR("MGI8", 8),
+ FIELDLIST_NAMESTR("MGI9", 8),
+ FIELDLIST_NAMESTR("MGIA", 8),
+ FIELDLIST_NAMESTR("MGIB", 8),
+ FIELDLIST_NAMESTR("MGIC", 8),
+ FIELDLIST_NAMESTR("MGID", 8),
+ FIELDLIST_NAMESTR("MGIE", 8),
+ FIELDLIST_NAMESTR("MGIF", 8),
+ FIELDLIST_NAMESTR("MGO0", 8),
+ FIELDLIST_NAMESTR("MGO1", 8),
+ FIELDLIST_NAMESTR("MGO2", 8),
+ FIELDLIST_NAMESTR("MGO3", 8),
+ FIELDLIST_NAMESTR("MGO4", 8),
+ FIELDLIST_NAMESTR("MGO5", 8),
+ FIELDLIST_NAMESTR("MGO6", 8),
+ FIELDLIST_NAMESTR("MGO7", 8),
+ FIELDLIST_NAMESTR("MGO8", 8),
+ FIELDLIST_NAMESTR("MGO9", 8),
+ FIELDLIST_NAMESTR("MGOA", 8),
+ FIELDLIST_NAMESTR("MGOB", 8),
+ FIELDLIST_NAMESTR("MGOC", 8),
+ FIELDLIST_NAMESTR("MGOD", 8),
+ FIELDLIST_NAMESTR("MGOE", 8),
+ FIELDLIST_NAMESTR("MGOF", 8),
+};
+static const size_t ucsi_region_len = ARRAY_SIZE(ucsi_region_fields);
+
static void wilco_ec_post_complete(void *unused)
{
wilco_ec_send(KB_BIOS_PROGRESS, BIOS_PROGRESS_POST_COMPLETE);
@@ -111,11 +172,47 @@ static void wilco_ec_read_resources(struct device *dev)
wilco_ec_resource(dev, 2, CONFIG_EC_BASE_PACKET, 16);
}
+static void wilco_ec_fill_ssdt_generator(struct device *dev)
+{
+ struct opregion opreg;
+ void *region_ptr;
+
+ if (!dev->enabled)
+ return;
+
+ region_ptr = cbmem_add(CBMEM_ID_ACPI_UCSI, ucsi_region_len);
+ if (!region_ptr)
+ return;
+ memset(region_ptr, 0, ucsi_region_len);
+
+ opreg.name = "UCSM";
+ opreg.regionspace = SYSTEMMEMORY;
+ opreg.regionoffset = (uintptr_t)region_ptr;
+ opreg.regionlen = ucsi_region_len;
+
+ acpigen_write_scope(acpi_device_path_join(dev, "UCSI"));
+ acpigen_write_name("_CRS");
+ acpigen_write_resourcetemplate_header();
+ acpigen_write_mem32fixed(1, (uintptr_t)region_ptr, ucsi_region_len);
+ acpigen_write_resourcetemplate_footer();
+ acpigen_write_opregion(&opreg);
+ acpigen_write_field(opreg.name, ucsi_region_fields, ucsi_region_len,
+ FIELD_ANYACC | FIELD_LOCK | FIELD_PRESERVE);
+ acpigen_pop_len(); /* Scope */
+}
+
+static const char *wilco_ec_acpi_name(const struct device *dev)
+{
+ return "EC0";
+}
+
static struct device_operations ops = {
- .init = wilco_ec_init,
- .read_resources = wilco_ec_read_resources,
- .enable_resources = DEVICE_NOOP,
- .set_resources = DEVICE_NOOP,
+ .init = wilco_ec_init,
+ .read_resources = wilco_ec_read_resources,
+ .enable_resources = DEVICE_NOOP,
+ .set_resources = DEVICE_NOOP,
+ .acpi_fill_ssdt_generator = wilco_ec_fill_ssdt_generator,
+ .acpi_name = wilco_ec_acpi_name,
};
static struct pnp_info info[] = {