diff --git a/src/soc/mediatek/mt8196/include/soc/mt6685_rtc.h b/src/soc/mediatek/mt8196/include/soc/mt6685_rtc.h index e46fd90ff6..612d2d424e 100644 --- a/src/soc/mediatek/mt8196/include/soc/mt6685_rtc.h +++ b/src/soc/mediatek/mt8196/include/soc/mt6685_rtc.h @@ -49,6 +49,11 @@ #define RG_FQMTR_DATA 0x54a +#define RTC_SPAR_MACRO 0x5d8 +#define RTC_SPAR_PROT_STAT_SHIFT 6 +#define RTC_SPAR_PROT_STAT_MASK 0x3 +#define RTC_PROT_UNLOCK_SUCCESS 0x3 + #define RG_FQMTR_CLK_CK_PDN_SET 0x10c #define RG_FQMTR_CLK_CK_PDN_MASK 0x1 #define RG_FQMTR_CLK_CK_PDN_SHIFT 5 diff --git a/src/soc/mediatek/mt8196/include/soc/rtc.h b/src/soc/mediatek/mt8196/include/soc/rtc.h index b315998713..f45e4384ce 100644 --- a/src/soc/mediatek/mt8196/include/soc/rtc.h +++ b/src/soc/mediatek/mt8196/include/soc/rtc.h @@ -12,6 +12,7 @@ #include #include #include +#include #include /* RTC registers */ @@ -21,7 +22,7 @@ enum { RTC_BBPU_RELOAD = BIT(5), RTC_BBPU_CBUSY = BIT(6), - RTC_CBUSY_TIMEOUT_US = 8000, + RTC_CBUSY_TIMEOUT_US = USECS_PER_SEC, }; enum { @@ -59,6 +60,7 @@ enum { #define BBPU_RELOAD_TIMEOUT_US 100000 #define EOSC_CHECK_CLK_TIMEOUT_US 1000000 #define RECOVERY_RETRY_COUNT 3 +#define PROT_UNLOCK_RETRY_COUNT 3 struct rtc_clk_freq { u16 fqm26m_ck; diff --git a/src/soc/mediatek/mt8196/mt6685_rtc.c b/src/soc/mediatek/mt8196/mt6685_rtc.c index 95e8dd6907..36e29f5a2a 100644 --- a/src/soc/mediatek/mt8196/mt6685_rtc.c +++ b/src/soc/mediatek/mt8196/mt6685_rtc.c @@ -33,6 +33,34 @@ void rtc_write(u16 addr, u16 wdata) mt6685_write16(addr, wdata); } +static u16 rtc_get_prot_stat(void) +{ + u16 val; + u16 state = 0; + + udelay(100); + + rtc_read(RTC_SPAR_MACRO, &val); + + state = (val >> RTC_SPAR_PROT_STAT_SHIFT) & RTC_SPAR_PROT_STAT_MASK; + + return state; +} + +static bool mt6685_writeif_unlock(void) +{ + if (!retry(PROT_UNLOCK_RETRY_COUNT, + rtc_writeif_unlock() && + rtc_get_prot_stat() == RTC_PROT_UNLOCK_SUCCESS)) { + + printk(BIOS_ERR, "%s: retry failed!!\n", __func__); + + return false; + } + + return true; +} + static bool rtc_eosc_check_clock(const struct rtc_clk_freq *result) { if ((result->fqm26m_ck >= 3 && result->fqm26m_ck <= 7) && @@ -319,7 +347,7 @@ static bool rtc_init_after_recovery(void) /* write powerkeys */ if (!rtc_powerkey_init()) return false; - if (!rtc_writeif_unlock()) + if (!mt6685_writeif_unlock()) return false; if (!rtc_gpio_init()) return false; @@ -332,7 +360,7 @@ static bool rtc_init_after_recovery(void) if (!rtc_powerkey_init()) return false; - if (!rtc_writeif_unlock()) + if (!mt6685_writeif_unlock()) return false; secure_rtc_init(); @@ -366,9 +394,9 @@ static bool rtc_first_boot_init(void) if (!rtc_write_trigger()) return false; - if (!rtc_writeif_unlock()) { + if (!mt6685_writeif_unlock()) { printk(BIOS_ERR, - "%s: rtc_writeif_unlock failed after BBPU written\n", __func__); + "%s: mt6685_writeif_unlock failed after BBPU written\n", __func__); return false; } @@ -387,9 +415,9 @@ static bool rtc_first_boot_init(void) return false; } - if (!rtc_writeif_unlock()) { + if (!mt6685_writeif_unlock()) { printk(BIOS_ERR, - "%s: rtc_writeif_unlock failed after POWERKEY written\n", __func__); + "%s: mt6685_writeif_unlock failed after POWERKEY written\n", __func__); return false; } @@ -402,9 +430,9 @@ static bool rtc_first_boot_init(void) return false; } - if (!rtc_writeif_unlock()) { + if (!mt6685_writeif_unlock()) { printk(BIOS_ERR, - "%s rtc_writeif_unlock failed after BBPU written\n", __func__); + "%s mt6685_writeif_unlock failed after BBPU written\n", __func__); return false; } @@ -418,9 +446,9 @@ static bool rtc_first_boot_init(void) return false; } - if (!rtc_writeif_unlock()) { + if (!mt6685_writeif_unlock()) { printk(BIOS_ERR, - "%s rtc_writeif_unlock failed after POWERKEY written\n", __func__); + "%s mt6685_writeif_unlock failed after POWERKEY written\n", __func__); return false; } @@ -444,8 +472,8 @@ static void rtc_enable_dcxo(void) u16 con, osc32con, sec; /* Unlock for reload */ - if (!rtc_writeif_unlock()) - printk(BIOS_ERR, "rtc_writeif_unlock() failed\n"); + if (!mt6685_writeif_unlock()) + printk(BIOS_ERR, "mt6685_writeif_unlock() failed\n"); rtc_read(RTC_BBPU, &rdata); rtc_write(RTC_BBPU, rdata | RTC_BBPU_KEY | RTC_BBPU_RELOAD); @@ -525,7 +553,7 @@ void rtc_boot(void) rtc_read(RTC_BBPU, &rtc_bbpu); rtc_write(RTC_BBPU, rtc_bbpu | RTC_BBPU_KEY | RTC_BBPU_RELOAD); - if (!rtc_write_trigger() || !rtc_writeif_unlock()) { + if (!rtc_write_trigger() || !mt6685_writeif_unlock()) { rtc_recovery_flow(); } else { rtc_read(RTC_POWERKEY1, &rtc_pwrkey1);