blob: 4147a0ff75eae8ed6ff46e898c13c754f4f41536 [file] [log] [blame]
Tianping Fang11f4a292015-07-31 17:10:58 +08001/*
2 * This file is part of the coreboot project.
3 *
4 * Copyright 2015 MediaTek Inc.
5 *
6 * This program is free software; you can redistribute it and/or modify
7 * it under the terms of the GNU General Public License as published by
8 * the Free Software Foundation; version 2 of the License.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 */
15
16#include <assert.h>
17#include <bcd.h>
18#include <console/console.h>
19#include <delay.h>
20#include <rtc.h>
21#include <timer.h>
22
23#include <soc/mt6391.h>
24#include <soc/pmic_wrap.h>
25#include <soc/rtc.h>
26
27#define RTC_GPIO_USER_MASK ((1 << 13) - (1 << 8))
28
29/* ensure rtc write success */
30static inline int rtc_busy_wait(void)
31{
32 struct stopwatch sw;
33 u16 bbpu;
34
35 stopwatch_init_usecs_expire(&sw, RTC_CBUSY_TIMEOUT_US);
36
37 do {
38 pwrap_read(RTC_BBPU, &bbpu);
39 /* Time > 1sec, time out and set recovery mode enable.*/
40 if (stopwatch_expired(&sw)) {
41 printk(BIOS_INFO, "[RTC] BBPU CBUSY time out !!\n");
42 return 0;
43 }
44 } while (bbpu & RTC_BBPU_CBUSY);
45
46 return 1;
47}
48
49static int write_trigger(void)
50{
51 pwrap_write(RTC_WRTGR, 1);
52 return rtc_busy_wait();
53}
54
55/* unlock rtc write interface */
56static int writeif_unlock(void)
57{
58 pwrap_write(RTC_PROT, RTC_PROT_UNLOCK1);
59 if (!write_trigger())
60 return 0;
61 pwrap_write(RTC_PROT, RTC_PROT_UNLOCK2);
62 if (!write_trigger())
63 return 0;
64
65 return 1;
66}
67
68/* set rtc time */
69int rtc_set(const struct rtc_time *time)
70{
71 return -1;
72}
73
74/* get rtc time */
75int rtc_get(struct rtc_time *time)
76{
77 u16 value;
78
79 pwrap_read(RTC_TC_SEC, &value);
80 time->sec = value;
81 pwrap_read(RTC_TC_MIN, &value);
82 time->min = value;
83 pwrap_read(RTC_TC_HOU, &value);
84 time->hour = value;
85 pwrap_read(RTC_TC_DOM, &value);
86 time->mday = value;
87 pwrap_read(RTC_TC_MTH, &value);
88 time->mon = value;
89 pwrap_read(RTC_TC_YEA, &value);
90 time->year = (value + RTC_MIN_YEAR_OFFSET) % 100;
91
92 return 0;
93}
94
95/* set rtc xosc setting */
96static void rtc_xosc_write(u16 val)
97{
98 pwrap_write(RTC_OSC32CON, RTC_OSC32CON_UNLOCK1);
99 udelay(200);
100 pwrap_write(RTC_OSC32CON, RTC_OSC32CON_UNLOCK2);
101 udelay(200);
102
103 pwrap_write(RTC_OSC32CON, val);
104 udelay(200);
105 mt6391_write(RTC_BBPU, RTC_BBPU_KEY | RTC_BBPU_RELOAD, 0, 0);
106 write_trigger();
107}
108
109/* initialize rtc related registers */
110static int rtc_reg_init(void)
111{
112 u16 irqsta;
113
114 pwrap_write(RTC_IRQ_EN, 0);
115 pwrap_write(RTC_CII_EN, 0);
116 pwrap_write(RTC_AL_MASK, 0);
117 pwrap_write(RTC_AL_YEA, 1970 - RTC_MIN_YEAR);
118 pwrap_write(RTC_AL_MTH, 1);
119 pwrap_write(RTC_AL_DOM, 1);
120 pwrap_write(RTC_AL_DOW, 4);
121 pwrap_write(RTC_AL_HOU, 0);
122 pwrap_write(RTC_AL_MIN, 0);
123 pwrap_write(RTC_AL_SEC, 0);
124
125 pwrap_write(RTC_DIFF, 0);
126 pwrap_write(RTC_CALI, 0);
127 if (!write_trigger())
128 return 0;
129
130 pwrap_read(RTC_IRQ_STA, &irqsta); /* read clear */
131
132 /* init time counters after resetting RTC_DIFF and RTC_CALI */
133 pwrap_write(RTC_TC_YEA, RTC_DEFAULT_YEA - RTC_MIN_YEAR);
134 pwrap_write(RTC_TC_MTH, RTC_DEFAULT_MTH);
135 pwrap_write(RTC_TC_DOM, RTC_DEFAULT_DOM);
136 pwrap_write(RTC_TC_DOW, RTC_DEFAULT_DOW);
137 pwrap_write(RTC_TC_HOU, 0);
138 pwrap_write(RTC_TC_MIN, 0);
139 pwrap_write(RTC_TC_SEC, 0);
140
141 return write_trigger();
142}
143
144/* initialize rtc related gpio */
145static int rtc_gpio_init(void)
146{
147 u16 con;
148
149 mt6391_gpio_set_pull(3, MT6391_GPIO_PULL_DISABLE,
150 MT6391_GPIO_PULL_DOWN); /* RTC_32K1V8 */
151
152 /* Export 32K clock RTC_32K2V8 */
153 pwrap_read(RTC_CON, &con);
154 con &= (RTC_CON_LPSTA_RAW | RTC_CON_LPRST | RTC_CON_LPEN);
155 con |= (RTC_CON_GPEN | RTC_CON_GOE);
156 con &= ~(RTC_CON_F32KOB);
157 pwrap_write(RTC_CON, con);
158 return write_trigger();
159}
160
161/* set xosc mode */
162static void rtc_osc_init(void)
163{
164 u16 con;
165
166 /* enable 32K export */
167 rtc_gpio_init();
168
169 pwrap_write(PMIC_RG_TOP_CKTST2, 0x0);
170 pwrap_read(RTC_OSC32CON, &con);
171 if ((con & 0x1f) != 0x0) /* check XOSCCALI */
172 rtc_xosc_write(0x3);
173}
174
175/* low power detect setting */
176static int rtc_lpd_init(void)
177{
178 mt6391_write(RTC_CON, RTC_CON_LPEN, RTC_CON_LPRST, 0);
179 if (!write_trigger())
180 return 0;
181
182 mt6391_write(RTC_CON, RTC_CON_LPRST, 0, 0);
183 if (!write_trigger())
184 return 0;
185
186 mt6391_write(RTC_CON, 0, RTC_CON_LPRST, 0);
187 if (!write_trigger())
188 return 0;
189
190 return 1;
191}
192
193/* rtc init check */
194static int rtc_init(u8 recover)
195{
196 printk(BIOS_INFO, "[RTC] %s recovery: %d\n", __func__, recover);
197
198 if (!writeif_unlock())
199 return 0;
200
201 if (!rtc_gpio_init())
202 return 0;
203
204 /* Use SW to detect 32K mode instead of HW */
205 if (recover)
206 mt6391_write(PMIC_RG_CHRSTATUS, 0x4, 0x1, 9);
207
208 rtc_xosc_write(0x3);
209
210 if (recover)
211 mdelay(1000);
212
213 /* write powerkeys */
214 pwrap_write(RTC_POWERKEY1, RTC_POWERKEY1_KEY);
215 pwrap_write(RTC_POWERKEY2, RTC_POWERKEY2_KEY);
216 if (!write_trigger())
217 return 0;
218
219 if (recover)
220 mt6391_write(PMIC_RG_CHRSTATUS, 0, 0x4, 9);
221
222 rtc_xosc_write(0);
223
224 if (!rtc_reg_init())
225 return 0;
226 if (!rtc_lpd_init())
227 return 0;
228
229 return 1;
230}
231
232/* enable rtc bbpu */
233static void rtc_bbpu_power_on(void)
234{
235 u16 bbpu;
236 int ret;
237
238 /* pull PWRBB high */
239 bbpu = RTC_BBPU_KEY | RTC_BBPU_AUTO | RTC_BBPU_BBPU | RTC_BBPU_PWREN;
240 pwrap_write(RTC_BBPU, bbpu);
241 ret = write_trigger();
242 printk(BIOS_INFO, "[RTC] %s write_trigger=%d\n", __func__, ret);
243
244 /* enable DCXO to transform external 32KHz clock to 26MHz clock
245 directly sent to SoC */
246 mt6391_write(PMIC_RG_DCXO_FORCE_MODE1, BIT(11), 0, 0);
247 mt6391_write(PMIC_RG_DCXO_POR2_CON3,
248 BIT(8) | BIT(9) | BIT(10) | BIT(11), 0, 0);
249 mt6391_write(PMIC_RG_DCXO_CON2,
250 BIT(1) | BIT(3) | BIT(5) | BIT(6), 0, 0);
251
252 pwrap_read(RTC_BBPU, &bbpu);
253 printk(BIOS_INFO, "[RTC] %s done BBPU=%#x\n", __func__, bbpu);
254
255 /* detect hw clock done,close RG_RTC_75K_PDN for low power setting. */
256 mt6391_write(PMIC_RG_TOP_CKPDN2, 0x1, 0, 14);
257}
258
259static u8 rtc_check_state(void)
260{
261 u16 con;
262 u16 pwrky1;
263 u16 pwrky2;
264
265 pwrap_read(RTC_CON, &con);
266 pwrap_read(RTC_POWERKEY1, &pwrky1);
267 pwrap_read(RTC_POWERKEY2, &pwrky2);
268
269 if (con & RTC_CON_LPSTA_RAW)
270 return RTC_STATE_INIT;
271
272 if (!rtc_busy_wait())
273 return RTC_STATE_RECOVER;
274
275 if (!writeif_unlock())
276 return RTC_STATE_RECOVER;
277
278 if (pwrky1 != RTC_POWERKEY1_KEY || pwrky2 != RTC_POWERKEY2_KEY)
279 return RTC_STATE_INIT;
280 else
281 return RTC_STATE_REBOOT;
282}
283
284/* the rtc boot flow entry */
285void rtc_boot(void)
286{
287 u16 bbpu;
288 u16 con;
289 u16 irqsta;
290
291 pwrap_write(PMIC_RG_TOP_CKPDN, 0);
292 pwrap_write(PMIC_RG_TOP_CKPDN2, 0);
293
294 switch (rtc_check_state()) {
295 case RTC_STATE_REBOOT:
296 mt6391_write(RTC_BBPU, RTC_BBPU_KEY | RTC_BBPU_RELOAD, 0, 0);
297 write_trigger();
298 rtc_osc_init();
299 break;
300 case RTC_STATE_RECOVER:
301 rtc_init(1);
302 break;
303 case RTC_STATE_INIT:
304 default:
305 if (!rtc_init(0))
306 rtc_init(1);
307 break;
308 }
309
310 pwrap_read(RTC_IRQ_STA, &irqsta); /* Read clear */
311 pwrap_read(RTC_BBPU, &bbpu);
312 pwrap_read(RTC_CON, &con);
313
314 printk(BIOS_INFO, "[RTC] irqsta = %x", irqsta);
315 printk(BIOS_INFO, " bbpu = %#x, con = %#x\n", bbpu, con);
316 rtc_bbpu_power_on();
317}