diff --git a/src/soc/intel/common/block/gpio/gpio.c b/src/soc/intel/common/block/gpio/gpio.c index 4398c9fb62..db7654537a 100644 --- a/src/soc/intel/common/block/gpio/gpio.c +++ b/src/soc/intel/common/block/gpio/gpio.c @@ -763,3 +763,27 @@ static void snapshot_cleanup(void *unused) BOOT_STATE_INIT_ENTRY(BS_OS_RESUME, BS_ON_EXIT, snapshot_cleanup, NULL); BOOT_STATE_INIT_ENTRY(BS_PAYLOAD_LOAD, BS_ON_EXIT, snapshot_cleanup, NULL); + +bool gpio_get_vw_info(gpio_t pad, unsigned int *vw_index, unsigned int *vw_bit) +{ + const struct pad_community *comm; + unsigned int offset = 0; + size_t i; + + comm = gpio_get_community(pad); + for (i = 0; i < comm->num_vw_entries; i++) { + if (pad >= comm->vw_entries[i].first_pad && pad <= comm->vw_entries[i].last_pad) + break; + + offset += 1 + comm->vw_entries[i].last_pad - comm->vw_entries[i].first_pad; + } + + if (i == comm->num_vw_entries) + return false; + + offset += pad - comm->vw_entries[i].first_pad; + *vw_index = comm->vw_base + offset / 8; + *vw_bit = offset % 8; + + return true; +} diff --git a/src/soc/intel/common/block/include/intelblocks/gpio.h b/src/soc/intel/common/block/include/intelblocks/gpio.h index a7419dca59..eab257361e 100644 --- a/src/soc/intel/common/block/include/intelblocks/gpio.h +++ b/src/soc/intel/common/block/include/intelblocks/gpio.h @@ -96,6 +96,12 @@ struct pad_group { int acpi_pad_base; }; +/* A range of consecutive virtual-wire entries in a community */ +struct vw_entries { + gpio_t first_pad; + gpio_t last_pad; +}; + /* This structure will be used to describe a community or each group within a * community when multiple groups exist inside a community */ @@ -123,6 +129,13 @@ struct pad_community { size_t num_reset_vals; const struct pad_group *groups; size_t num_groups; + unsigned int vw_base; + /* + * Note: The entries must be in the same order here as the order in + * which they map to VW indexes (beginning with VW base) + */ + const struct vw_entries *vw_entries; + size_t num_vw_entries; }; /* @@ -237,5 +250,11 @@ bool gpio_routes_ioapic_irq(unsigned int irq); size_t gpio_get_index_in_group(gpio_t pad); +/* + * Returns true and stuffs out params for virtual-wire index and bit position + * for the given GPIO, otherwise false if there is no VW index for the pad. + */ +bool gpio_get_vw_info(gpio_t pad, unsigned int *vw_index, unsigned int *vw_bit); + #endif #endif /* _SOC_INTELBLOCKS_GPIO_H_ */