diff options
Diffstat (limited to 'src')
6 files changed, 145 insertions, 23 deletions
diff --git a/src/mainboard/google/guybrush/bootblock.c b/src/mainboard/google/guybrush/bootblock.c index f9f1ab034f..dc5e04657b 100644 --- a/src/mainboard/google/guybrush/bootblock.c +++ b/src/mainboard/google/guybrush/bootblock.c @@ -5,8 +5,13 @@ #include <bootblock_common.h> #include <baseboard/variants.h> #include <console/console.h> +#include <delay.h> #include <device/pci_ops.h> #include <soc/pci_devs.h> +#include <timer.h> + +#define FC350_PCIE_INIT_DELAY_US (20 * USECS_PER_MSEC) +struct stopwatch pcie_init_timeout_sw; void mb_set_up_early_espi(void) { @@ -22,13 +27,21 @@ void mb_set_up_early_espi(void) void bootblock_mainboard_early_init(void) { - size_t num_gpios; uint32_t dword; - const struct soc_amd_gpio *gpios; + size_t base_num_gpios, override_num_gpios; + const struct soc_amd_gpio *base_gpios, *override_gpios; if (!CONFIG(VBOOT_STARTS_BEFORE_BOOTBLOCK)) { - gpios = variant_early_gpio_table(&num_gpios); - program_gpios(gpios, num_gpios); + base_gpios = variant_early_gpio_table(&base_num_gpios); + override_gpios = variant_early_override_gpio_table(&override_num_gpios); + + gpio_configure_pads_with_override(base_gpios, base_num_gpios, + override_gpios, override_num_gpios); + + /* Set a timer to make sure there's enough delay for + * the Fibocom 350 PCIe init + */ + stopwatch_init_usecs_expire(&pcie_init_timeout_sw, FC350_PCIE_INIT_DELAY_US); } printk(BIOS_DEBUG, "Bootblock configure eSPI\n"); @@ -51,7 +64,31 @@ void bootblock_mainboard_early_init(void) void bootblock_mainboard_init(void) { - /* Put FPMCU check after EC initialization */ + size_t base_num_gpios, override_num_gpios; + const struct soc_amd_gpio *base_gpios, *override_gpios; + int i = 0; + + /* Make sure that at least 20ms has elapsed since enabling WWAN power + * in bootblock_mainboard_early_init. + * This is only applicable if verstage is not in the PSP and the board + * is using the fibocom 350 WLAN card, so this typically will not be hit. + */ + if (!CONFIG(VBOOT_STARTS_BEFORE_BOOTBLOCK) && variant_has_pcie_wwan()) { + while (!stopwatch_expired(&pcie_init_timeout_sw)) { + mdelay(1); + i++; + }; + if (i) + printk(BIOS_DEBUG, "Delayed %d ms for PCIe\n", i); + } + + base_gpios = variant_bootblock_gpio_table(&base_num_gpios); + override_gpios = variant_bootblock_override_gpio_table(&override_num_gpios); + + gpio_configure_pads_with_override(base_gpios, base_num_gpios, override_gpios, + override_num_gpios); + + /* FPMCU check needs to happen after EC initialization for FW_CONFIG bits */ if (variant_has_fpmcu()) variant_fpmcu_reset(); } diff --git a/src/mainboard/google/guybrush/port_descriptors.c b/src/mainboard/google/guybrush/port_descriptors.c index 489bccdec0..a83db6cd1f 100644 --- a/src/mainboard/google/guybrush/port_descriptors.c +++ b/src/mainboard/google/guybrush/port_descriptors.c @@ -6,7 +6,7 @@ #include <soc/gpio.h> #include <types.h> -/* TODO: test if this really works */ +/* All PCIe Resets are handled in coreboot */ static const fsp_dxio_descriptor guybrush_czn_dxio_descriptors[] = { { /* WLAN */ .engine_type = PCIE_ENGINE, @@ -18,7 +18,6 @@ static const fsp_dxio_descriptor guybrush_czn_dxio_descriptors[] = { .link_aspm = ASPM_L1, .turn_off_unused_lanes = true, .clk_req = CLK_REQ0, - .gpio_group_id = GPIO_29, .port_params = {PP_PSPP_AC, 0x133, PP_PSPP_DC, 0x122} }, { /* SD */ @@ -31,7 +30,6 @@ static const fsp_dxio_descriptor guybrush_czn_dxio_descriptors[] = { .link_aspm = ASPM_L1, .turn_off_unused_lanes = true, .clk_req = CLK_REQ1, - .gpio_group_id = GPIO_70, .port_params = {PP_PSPP_AC, 0x133, PP_PSPP_DC, 0x122} }, { /* WWAN */ @@ -44,7 +42,6 @@ static const fsp_dxio_descriptor guybrush_czn_dxio_descriptors[] = { .link_aspm = ASPM_L1, .turn_off_unused_lanes = true, .clk_req = CLK_REQ2, - .gpio_group_id = GPIO_18, .port_params = {PP_PSPP_AC, 0x133, PP_PSPP_DC, 0x122} }, { /* NVME */ @@ -57,7 +54,6 @@ static const fsp_dxio_descriptor guybrush_czn_dxio_descriptors[] = { .link_aspm = ASPM_L1, .turn_off_unused_lanes = true, .clk_req = CLK_REQ3, - .gpio_group_id = GPIO_40, .port_params = {PP_PSPP_AC, 0x133, PP_PSPP_DC, 0x122} }, { /* TODO: remove this temporay workaround */ diff --git a/src/mainboard/google/guybrush/variants/baseboard/gpio.c b/src/mainboard/google/guybrush/variants/baseboard/gpio.c index eb42ab505f..dc72cdb5c6 100644 --- a/src/mainboard/google/guybrush/variants/baseboard/gpio.c +++ b/src/mainboard/google/guybrush/variants/baseboard/gpio.c @@ -7,6 +7,7 @@ #include <soc/gpio.h> /* GPIO configuration in ramstage*/ +/* Please make sure that *ALL* GPIOs are configured in this table */ static const struct soc_amd_gpio base_gpio_table[] = { /* PWR_BTN_L */ PAD_NF(GPIO_0, PWR_BTN_L, PULL_NONE), @@ -40,7 +41,7 @@ static const struct soc_amd_gpio base_gpio_table[] = { /* SOC_SAR_INT_L */ PAD_SCI(GPIO_17, PULL_NONE, EDGE_LOW), /* WWAN_AUX_RESET_L */ - PAD_GPO(GPIO_18, LOW), + PAD_GPO(GPIO_18, HIGH), /* I2C3_SCL */ PAD_NF(GPIO_19, I2C3_SCL, PULL_NONE), /* I2C3_SDA */ @@ -55,12 +56,11 @@ static const struct soc_amd_gpio base_gpio_table[] = { PAD_GPO(GPIO_24, HIGH), /* GPIO_25: Not available */ /* PCIE_RST0_L */ - /* TODO: change back to PCIE_RST_L when we figure out why PCIE_RST doesn't go high. */ - PAD_GPO(GPIO_26, HIGH), + PAD_NFO(GPIO_26, PCIE_RST_L, HIGH), /* PCIE_RST1_L */ PAD_NF(GPIO_27, PCIE_RST1_L, PULL_NONE), /* GPIO_28: Not available */ - /* WLAN_AUX_RESET */ + /* WLAN_AUX_RESET (Active HIGH)*/ PAD_GPO(GPIO_29, LOW), /* ESPI_CS_L */ PAD_NF(GPIO_30, ESPI_CS_L, PULL_NONE), @@ -167,22 +167,32 @@ static const struct soc_amd_gpio base_gpio_table[] = { /* Early GPIO configuration */ static const struct soc_amd_gpio early_gpio_table[] = { + /* WWAN_AUX_RESET_L */ + PAD_GPO(GPIO_18, LOW), + /* WLAN_AUX_RESET (ACTIVE HIGH) */ + PAD_GPO(GPIO_29, HIGH), + /* SSD_AUX_RESET_L */ + PAD_GPO(GPIO_40, LOW), + /* SD_AUX_RESET_L */ + PAD_GPO(GPIO_69, LOW), + /* Guybrush BID>1: Unused TP27; BID==1: SD_AUX_RESET_L */ + PAD_NC(GPIO_70), + /* PCIE_RST0_L */ + PAD_NFO(GPIO_26, PCIE_RST_L, HIGH), + +/* Power on WLAN & WWAN */ /* EN_PP3300_WLAN */ PAD_GPO(GPIO_6, HIGH), /* EN_PWR_WWAN_X */ PAD_GPO(GPIO_8, HIGH), - /* WWAN_DISABLE */ - PAD_GPO(GPIO_85, LOW), - /* WLAN_DISABLE */ - PAD_GPO(GPIO_130, LOW), + +/* Enable ESPI, GSC Interrupt & I2C Communication */ /* GSC_SOC_INT_L */ PAD_INT(GPIO_3, PULL_NONE, EDGE_LOW, STATUS_DELIVERY), /* I2C3_SCL */ PAD_NF(GPIO_19, I2C3_SCL, PULL_NONE), /* I2C3_SDA */ PAD_NF(GPIO_20, I2C3_SDA, PULL_NONE), - /* PCIE_RST0_L */ - PAD_GPO(GPIO_26, HIGH), /* ESPI_CS_L */ PAD_NF(GPIO_30, ESPI_CS_L, PULL_NONE), /* ESPI_SOC_CLK */ @@ -197,17 +207,58 @@ static const struct soc_amd_gpio early_gpio_table[] = { PAD_NF(GPIO_107, SPI2_HOLD_L_ESPI2_D3, PULL_NONE), /* ESPI_ALERT_L */ PAD_NF(GPIO_108, ESPI_ALERT_D1, PULL_NONE), + +/* Enable UART 0 */ /* UART0_RXD */ PAD_NF(GPIO_141, UART0_RXD, PULL_NONE), /* UART0_TXD */ PAD_NF(GPIO_143, UART0_TXD, PULL_NONE), }; +/* Power-on timing requirements: + * Fibocom 350-GL: + * FCP0# goes high (GPIO 6) to Reset# high (GPIO 24): 20ms min + * FCP0# goes high (GPIO 6) to PERST# high (GPIO 26): 100ms min + * PERST# high (GPIO 26) to PCIE Training (FSP-M): 23ms min + * + * Realtek RTL8852AE: + * Power (3.3 V) valid to PERST# high (GPIO_26): 50ms min + * + * Qualcomm WCN6856: + * Power (3.3 V) valid to PERST# high (GPIO_26): 50ms min + * + * RTS5250S / RTS5227S / RTS5261S + * Power (3.3 V) valid to PERST# high (GPIO_69/70): 1ms min + * + * PCIe spec: + * Power (3.3 V) valid to PERST# high (GPIO_26): 50ms min (SUGGESTED) + * + * NVME adapters planned for Guybrush: + * No power on timings specified - Assumed to require PCIe Spec suggested + * guidelines. Testing seems to bear out this assumption. + */ + +static const struct soc_amd_gpio bootblock_gpio_table[] = { +/* Enable WWAN & WLAN */ + /* WWAN_RST_L */ + PAD_GPO(GPIO_24, HIGH), + /* WWAN_DISABLE */ + PAD_GPO(GPIO_85, LOW), + /* WLAN_DISABLE */ + PAD_GPO(GPIO_130, LOW), +}; + /* GPIO configuration for sleep */ static const struct soc_amd_gpio sleep_gpio_table[] = { /* TODO: Fill sleep gpio configuration */ }; +const struct soc_amd_gpio *__weak variant_bootblock_gpio_table(size_t *size) +{ + *size = ARRAY_SIZE(bootblock_gpio_table); + return bootblock_gpio_table; +} + const struct soc_amd_gpio *__weak variant_base_gpio_table(size_t *size) { *size = ARRAY_SIZE(base_gpio_table); @@ -219,6 +270,18 @@ const struct soc_amd_gpio *__weak variant_override_gpio_table(size_t *size) return NULL; } +const struct soc_amd_gpio * __weak variant_early_override_gpio_table(size_t *size) +{ + *size = 0; + return NULL; +} + +const struct soc_amd_gpio * __weak variant_bootblock_override_gpio_table(size_t *size) +{ + *size = 0; + return NULL; +} + const struct soc_amd_gpio *__weak variant_early_gpio_table(size_t *size) { *size = ARRAY_SIZE(early_gpio_table); diff --git a/src/mainboard/google/guybrush/variants/baseboard/include/baseboard/variants.h b/src/mainboard/google/guybrush/variants/baseboard/include/baseboard/variants.h index 6b82d183d7..f1bbfd3b46 100644 --- a/src/mainboard/google/guybrush/variants/baseboard/include/baseboard/variants.h +++ b/src/mainboard/google/guybrush/variants/baseboard/include/baseboard/variants.h @@ -19,14 +19,19 @@ */ const struct soc_amd_gpio *variant_base_gpio_table(size_t *size); /* - * This function allows variant to override any GPIOs that are different than the base GPIO - * configuration provided by variant_base_gpio_table(). + * These functions allow variants to override any GPIOs that are different than the base GPIO + * configuration provided without having to replace the entire file. */ const struct soc_amd_gpio *variant_override_gpio_table(size_t *size); +const struct soc_amd_gpio *variant_early_override_gpio_table(size_t *size); +const struct soc_amd_gpio *variant_bootblock_override_gpio_table(size_t *size); -/* This function provides early GPIO init in bootblock or psp. */ +/* This function provides early GPIO init in early bootblock or psp. */ const struct soc_amd_gpio *variant_early_gpio_table(size_t *size); +/* This function provides GPIO settings at the end of bootblock. */ +const struct soc_amd_gpio *variant_bootblock_gpio_table(size_t *size); + /* This function provides GPIO settings before entering sleep. */ const struct soc_amd_gpio *variant_sleep_gpio_table(size_t *size); diff --git a/src/mainboard/google/guybrush/variants/guybrush/Makefile.inc b/src/mainboard/google/guybrush/variants/guybrush/Makefile.inc index ba8514c4c2..8255ba8ebf 100644 --- a/src/mainboard/google/guybrush/variants/guybrush/Makefile.inc +++ b/src/mainboard/google/guybrush/variants/guybrush/Makefile.inc @@ -1,5 +1,6 @@ # SPDX-License-Identifier: GPL-2.0-or-later +bootblock-y += gpio.c ramstage-y += gpio.c subdirs-y += ./memory diff --git a/src/mainboard/google/guybrush/variants/guybrush/gpio.c b/src/mainboard/google/guybrush/variants/guybrush/gpio.c index 05c1542124..e71ed9d57a 100644 --- a/src/mainboard/google/guybrush/variants/guybrush/gpio.c +++ b/src/mainboard/google/guybrush/variants/guybrush/gpio.c @@ -18,6 +18,13 @@ static const struct soc_amd_gpio bid1_gpio_table[] = { PAD_GPI(GPIO_74, PULL_NONE), }; +/* This table is used by guybrush variant with board version < 2. */ +/* Use AUX Reset lines instead of PCIE_RST for Board Version 1 */ +static const struct soc_amd_gpio bid1_early_gpio_table[] = { + /* SD_AUX_RESET_L */ + PAD_GPO(GPIO_70, HIGH), +}; + const struct soc_amd_gpio *variant_override_gpio_table(size_t *size) { uint32_t board_version = board_id(); @@ -30,3 +37,16 @@ const struct soc_amd_gpio *variant_override_gpio_table(size_t *size) return NULL; } + +const struct soc_amd_gpio *variant_early_override_gpio_table(size_t *size) +{ + uint32_t board_version = board_id(); + *size = 0; + + if (board_version < 2) { + *size = ARRAY_SIZE(bid1_early_gpio_table); + return bid1_early_gpio_table; + } + + return NULL; +} |