wang qii has uploaded this change for review. ( https://review.coreboot.org/c/coreboot/+/30974
Change subject: mediatek/mt8183: Support gpio eh and rsel setting for I2C ......................................................................
mediatek/mt8183: Support gpio eh and rsel setting for I2C
The setting of these registers are only for i2c pin.
BUG=b:80501386 BRANCH=none TEST=Boot correctly on Kukui
Change-Id: I518ca07645fe55aa55e94e4f98178baa0b74a882 Signed-off-by: jg_poxu jg_poxu@mediatek.com --- M src/soc/mediatek/mt8183/gpio.c M src/soc/mediatek/mt8183/include/soc/gpio.h 2 files changed, 67 insertions(+), 1 deletion(-)
git pull ssh://review.coreboot.org:29418/coreboot refs/changes/74/30974/1
diff --git a/src/soc/mediatek/mt8183/gpio.c b/src/soc/mediatek/mt8183/gpio.c index d555c33..c87509a 100644 --- a/src/soc/mediatek/mt8183/gpio.c +++ b/src/soc/mediatek/mt8183/gpio.c @@ -15,10 +15,12 @@
#include <arch/io.h> #include <gpio.h> +#include <assert.h>
enum { EN_OFFSET = 0x60, SEL_OFFSET = 0x80, + EH_RSEL_OFFSET = 0xF0, };
static void gpio_set_pull_pupd(gpio_t gpio, enum pull_enable enable, @@ -67,3 +69,66 @@ else gpio_set_pull_en_sel(gpio, enable, select); } + +struct i2c_pin_spec { + uint16_t id; + uint8_t eh_bit; + uint8_t rsel_bit; +}; + +#define MTK_I2C_PIN_SPEC(pad_id, eh, rsel) \ + { \ + .id = pad_id, \ + .eh_bit = eh, \ + .rsel_bit = rsel, \ + } + +static const struct i2c_pin_spec i2c_pin_spec_list[] = { + MTK_I2C_PIN_SPEC(PAD_SCL5_ID, 20, 18), + MTK_I2C_PIN_SPEC(PAD_SDA5_ID, 15, 13), + MTK_I2C_PIN_SPEC(PAD_SCL3_ID, 12, 10), + MTK_I2C_PIN_SPEC(PAD_SDA3_ID, 7, 5), + MTK_I2C_PIN_SPEC(PAD_SDA1_ID, 12, 7), + MTK_I2C_PIN_SPEC(PAD_SDA0_ID, 9, 5), + MTK_I2C_PIN_SPEC(PAD_SCL0_ID, 19, 15), + MTK_I2C_PIN_SPEC(PAD_SCL1_ID, 22, 17), + MTK_I2C_PIN_SPEC(PAD_SCL2_ID, 24, 20), + MTK_I2C_PIN_SPEC(PAD_SDA2_ID, 14, 10), + MTK_I2C_PIN_SPEC(PAD_SCL4_ID, 27, 22), + MTK_I2C_PIN_SPEC(PAD_SDA4_ID, 17, 12), +}; + +static const struct i2c_pin_spec *get_i2c_pin_spec(gpio_t gpio) +{ + size_t i; + + for (i = 0; i < ARRAY_SIZE(i2c_pin_spec_list); i++) + if (gpio.id == i2c_pin_spec_list[i].id) + return &i2c_pin_spec_list[i]; + + return NULL; +} + +void gpio_set_i2c_eh(gpio_t gpio, uint32_t select) +{ + void *reg = GPIO_TO_IOCFG_BASE(gpio.base) + EH_RSEL_OFFSET; + uint8_t bit; + const struct i2c_pin_spec *pin = get_i2c_pin_spec(gpio); + + assert(pin); + assert(select < 8); + bit = pin->eh_bit; + clrsetbits_le32(reg, 7 << bit, select << bit); +} + +void gpio_set_i2c_rsel(gpio_t gpio, uint32_t select) +{ + void *reg = GPIO_TO_IOCFG_BASE(gpio.base) + EH_RSEL_OFFSET; + uint8_t bit; + const struct i2c_pin_spec *pin = get_i2c_pin_spec(gpio); + + assert(pin); + assert(select < 4); + bit = pin->rsel_bit; + clrsetbits_le32(reg, 3 << bit, select << bit); +} diff --git a/src/soc/mediatek/mt8183/include/soc/gpio.h b/src/soc/mediatek/mt8183/include/soc/gpio.h index c3c8dda..a3a972b 100644 --- a/src/soc/mediatek/mt8183/include/soc/gpio.h +++ b/src/soc/mediatek/mt8183/include/soc/gpio.h @@ -616,5 +616,6 @@ check_member(gpio_regs, mode[22].val, 0x460);
static struct gpio_regs *const mtk_gpio = (void *)(GPIO_BASE); - +void gpio_set_i2c_eh(gpio_t gpio, uint32_t select); +void gpio_set_i2c_rsel(gpio_t gpio, uint32_t select); #endif