2 * Freescale i.MX28 Boot PMIC init
4 * Copyright (C) 2011 Marek Vasut <marek.vasut@gmail.com>
5 * on behalf of DENX Software Engineering GmbH
7 * See file CREDITS for list of people who contributed to this
10 * This program is free software; you can redistribute it and/or
11 * modify it under the terms of the GNU General Public License as
12 * published by the Free Software Foundation; either version 2 of
13 * the License, or (at your option) any later version.
15 * This program is distributed in the hope that it will be useful,
16 * but WITHOUT ANY WARRANTY; without even the implied warranty of
17 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
18 * GNU General Public License for more details.
20 * You should have received a copy of the GNU General Public License
21 * along with this program; if not, write to the Free Software
22 * Foundation, Inc., 59 Temple Place, Suite 330, Boston,
29 #include <asm/arch/imx-regs.h>
31 #include "mx28_init.h"
39 #define __arch_getl(a) arch_getl(a, __func__, __LINE__)
40 static inline unsigned int arch_getl(volatile void *addr,
41 const char *fn, unsigned int ln)
43 volatile unsigned int *a = addr;
44 unsigned int val = *a;
45 dprintf("%s@%d: Read %x from %p\n", fn, ln, val, addr);
49 #define __arch_putl(v, a) arch_putl(v, a, __func__, __LINE__)
50 static inline void arch_putl(unsigned int val, volatile void *addr,
51 const char *fn, unsigned int ln)
53 volatile unsigned int *a = addr;
55 dprintf("%s@%d: Writing %x to %p\n", fn, ln, val, addr);
61 __static int mx28_power_vdd5v_gt_vddio(void)
63 #ifndef CONFIG_SPL_FIXED_BATT_SUPPLY_
64 struct mx28_power_regs *power_regs =
65 (struct mx28_power_regs *)MXS_POWER_BASE;
66 int power_sts = readl(&power_regs->hw_power_sts);
68 dprintf("%s@%d: %d\n", __func__, __LINE__,
69 !!(power_sts & POWER_STS_VDD5V_GT_VDDIO));
70 return power_sts & POWER_STS_VDD5V_GT_VDDIO;
72 dprintf("%s@%d: 0\n", __func__, __LINE__);
77 __static int mx28_power_vbus_valid(void)
79 #ifndef CONFIG_SPL_FIXED_BATT_SUPPLY
80 struct mx28_power_regs *power_regs =
81 (struct mx28_power_regs *)MXS_POWER_BASE;
82 int power_5vctrl = readl(&power_regs->hw_power_5vctrl);
84 dprintf("%s@%d: 0\n", __func__, __LINE__,
85 !!(power_5vctrl & POWER_5VCTRL_VBUSVALID_5VDETECT));
86 return power_5vctrl & POWER_5VCTRL_VBUSVALID_5VDETECT;
88 dprintf("%s@%d: 0\n", __func__, __LINE__);
93 static void memdump(unsigned long addr, unsigned long len)
97 uint32_t *ptr = (void *)addr;
99 for (i = 0; i < len; i++) {
101 dprintf("\n%x:", &ptr[i]);
102 dprintf(" %x", ptr[i]);
108 //#undef CONFIG_SPL_FIXED_BATT_SUPPLY
110 __static void mx28_power_clock2xtal(void)
112 struct mx28_clkctrl_regs *clkctrl_regs =
113 (struct mx28_clkctrl_regs *)MXS_CLKCTRL_BASE;
115 dprintf("%s@%d: \n", __func__, __LINE__);
116 /* Set XTAL as CPU reference clock */
117 writel(CLKCTRL_CLKSEQ_BYPASS_CPU,
118 &clkctrl_regs->hw_clkctrl_clkseq_set);
121 __static void mx28_power_clock2pll(void)
123 struct mx28_clkctrl_regs *clkctrl_regs =
124 (struct mx28_clkctrl_regs *)MXS_CLKCTRL_BASE;
126 dprintf("%s@%d: \n", __func__, __LINE__);
127 writel(CLKCTRL_PLL0CTRL0_POWER,
128 &clkctrl_regs->hw_clkctrl_pll0ctrl0_set);
130 writel(CLKCTRL_CLKSEQ_BYPASS_CPU,
131 &clkctrl_regs->hw_clkctrl_clkseq_clr);
134 __static void mx28_power_clear_auto_restart(void)
136 struct mx28_rtc_regs *rtc_regs =
137 (struct mx28_rtc_regs *)MXS_RTC_BASE;
139 dprintf("%s@%d: \n", __func__, __LINE__);
140 writel(RTC_CTRL_SFTRST, &rtc_regs->hw_rtc_ctrl_clr);
141 while (readl(&rtc_regs->hw_rtc_ctrl) & RTC_CTRL_SFTRST)
144 writel(RTC_CTRL_CLKGATE, &rtc_regs->hw_rtc_ctrl_clr);
145 while (readl(&rtc_regs->hw_rtc_ctrl) & RTC_CTRL_CLKGATE)
147 #ifdef CONFIG_MACH_MX28EVK
149 * Due to the hardware design bug of mx28 EVK-A
150 * we need to set the AUTO_RESTART bit.
152 if (readl(&rtc_regs->hw_rtc_persistent0) & RTC_PERSISTENT0_AUTO_RESTART)
155 while (readl(&rtc_regs->hw_rtc_stat) & RTC_STAT_NEW_REGS_MASK)
158 setbits_le32(&rtc_regs->hw_rtc_persistent0,
159 RTC_PERSISTENT0_AUTO_RESTART);
160 writel(RTC_CTRL_FORCE_UPDATE, &rtc_regs->hw_rtc_ctrl_set);
161 writel(RTC_CTRL_FORCE_UPDATE, &rtc_regs->hw_rtc_ctrl_clr);
162 while (readl(&rtc_regs->hw_rtc_stat) & RTC_STAT_NEW_REGS_MASK)
164 while (readl(&rtc_regs->hw_rtc_stat) & RTC_STAT_STALE_REGS_MASK)
169 __static void mx28_power_set_linreg(void)
171 struct mx28_power_regs *power_regs =
172 (struct mx28_power_regs *)MXS_POWER_BASE;
174 dprintf("%s@%d: \n", __func__, __LINE__);
175 /* Set linear regulator 25mV below switching converter */
176 clrsetbits_le32(&power_regs->hw_power_vdddctrl,
177 POWER_VDDDCTRL_LINREG_OFFSET_MASK,
178 POWER_VDDDCTRL_LINREG_OFFSET_1STEPS_ABOVE);
180 clrsetbits_le32(&power_regs->hw_power_vddactrl,
181 POWER_VDDACTRL_LINREG_OFFSET_MASK,
182 POWER_VDDACTRL_LINREG_OFFSET_1STEPS_BELOW);
184 clrsetbits_le32(&power_regs->hw_power_vddioctrl,
185 POWER_VDDIOCTRL_LINREG_OFFSET_MASK,
186 POWER_VDDIOCTRL_LINREG_OFFSET_1STEPS_BELOW);
187 dprintf("%s@%d: vddioctrl=%x\n", __func__, __LINE__,
188 readl(&power_regs->hw_power_vddioctrl));
191 __static void mx28_src_power_init(void)
193 struct mx28_power_regs *power_regs =
194 (struct mx28_power_regs *)MXS_POWER_BASE;
196 dprintf("%s@%d: \n", __func__, __LINE__);
197 /* Improve efficieny and reduce transient ripple */
198 writel(POWER_LOOPCTRL_TOGGLE_DIF | POWER_LOOPCTRL_EN_CM_HYST |
199 POWER_LOOPCTRL_EN_DF_HYST, &power_regs->hw_power_loopctrl_set);
201 clrsetbits_le32(&power_regs->hw_power_dclimits,
202 POWER_DCLIMITS_POSLIMIT_BUCK_MASK,
203 0x30 << POWER_DCLIMITS_POSLIMIT_BUCK_OFFSET);
205 setbits_le32(&power_regs->hw_power_battmonitor,
206 POWER_BATTMONITOR_EN_BATADJ);
208 /* Increase the RCSCALE level for quick DCDC response to dynamic load */
209 clrsetbits_le32(&power_regs->hw_power_loopctrl,
210 POWER_LOOPCTRL_EN_RCSCALE_MASK,
211 POWER_LOOPCTRL_RCSCALE_THRESH |
212 POWER_LOOPCTRL_EN_RCSCALE_8X);
214 clrsetbits_le32(&power_regs->hw_power_minpwr,
215 POWER_MINPWR_HALFFETS, POWER_MINPWR_DOUBLE_FETS);
216 #ifndef CONFIG_SPL_FIXED_BATT_SUPPLY
217 /* 5V to battery handoff ... FIXME */
218 setbits_le32(&power_regs->hw_power_5vctrl, POWER_5VCTRL_DCDC_XFER);
220 clrbits_le32(&power_regs->hw_power_5vctrl, POWER_5VCTRL_DCDC_XFER);
224 void mx28_powerdown(void)
226 struct mx28_power_regs *power_regs =
227 (struct mx28_power_regs *)MXS_POWER_BASE;
229 dprintf("%s@%d: \n", __func__, __LINE__);
230 writel(POWER_RESET_UNLOCK_KEY, &power_regs->hw_power_reset);
231 writel(POWER_RESET_UNLOCK_KEY | POWER_RESET_PWD_OFF,
232 &power_regs->hw_power_reset);
235 __static void mx28_fixed_batt_boot(void)
237 struct mx28_power_regs *power_regs =
238 (struct mx28_power_regs *)MXS_POWER_BASE;
240 writel(POWER_5VCTRL_PWDN_5VBRNOUT,
241 &power_regs->hw_power_5vctrl_set);
242 writel(POWER_5VCTRL_ENABLE_DCDC,
243 &power_regs->hw_power_5vctrl_set);
245 writel(POWER_CHARGE_PWD_BATTCHRG, &power_regs->hw_power_charge_set);
247 clrsetbits_le32(&power_regs->hw_power_vdddctrl,
248 POWER_VDDDCTRL_DISABLE_FET |
249 POWER_VDDDCTRL_ENABLE_LINREG,
250 POWER_VDDDCTRL_DISABLE_STEPPING);
252 /* Stop 5V detection */
253 writel(POWER_5VCTRL_PWRUP_VBUS_CMPS,
254 &power_regs->hw_power_5vctrl_clr);
257 #ifndef CONFIG_SPL_FIXED_BATT_SUPPLY
258 #define BATT_BO_VALUE 15
260 /* Brownout at 3.08V */
261 #define BATT_BO_VALUE 17
264 __static void mx28_init_batt_bo(void)
266 struct mx28_power_regs *power_regs =
267 (struct mx28_power_regs *)MXS_POWER_BASE;
269 dprintf("%s@%d: \n", __func__, __LINE__);
270 #ifndef CONFIG_SPL_FIXED_BATT_SUPPLY
272 clrsetbits_le32(&power_regs->hw_power_battmonitor,
273 POWER_BATTMONITOR_BRWNOUT_LVL_MASK,
274 15 << POWER_BATTMONITOR_BRWNOUT_LVL_OFFSET);
276 writel(POWER_CTRL_BATT_BO_IRQ, &power_regs->hw_power_ctrl_clr);
277 writel(POWER_CTRL_ENIRQ_BATT_BO, &power_regs->hw_power_ctrl_clr);
279 setbits_le32(&power_regs->hw_power_battmonitor,
280 POWER_BATTMONITOR_PWDN_BATTBRNOUT);
281 writel(POWER_CTRL_BATT_BO_IRQ, &power_regs->hw_power_ctrl_clr);
285 __static void mx28_switch_vddd_to_dcdc_source(void)
287 struct mx28_power_regs *power_regs =
288 (struct mx28_power_regs *)MXS_POWER_BASE;
290 dprintf("%s@%d: \n", __func__, __LINE__);
291 clrsetbits_le32(&power_regs->hw_power_vdddctrl,
292 POWER_VDDDCTRL_LINREG_OFFSET_MASK,
293 POWER_VDDDCTRL_LINREG_OFFSET_1STEPS_BELOW);
295 clrsetbits_le32(&power_regs->hw_power_vdddctrl,
296 POWER_VDDDCTRL_DISABLE_FET | POWER_VDDDCTRL_DISABLE_STEPPING,
297 POWER_VDDDCTRL_ENABLE_LINREG);
300 __static void mx28_enable_output_rail_protection(void)
302 struct mx28_power_regs *power_regs =
303 (struct mx28_power_regs *)MXS_POWER_BASE;
305 writel(POWER_CTRL_VDDD_BO_IRQ | POWER_CTRL_VDDA_BO_IRQ |
306 POWER_CTRL_VDDIO_BO_IRQ, &power_regs->hw_power_ctrl_clr);
308 setbits_le32(&power_regs->hw_power_vdddctrl,
309 POWER_VDDDCTRL_PWDN_BRNOUT);
311 setbits_le32(&power_regs->hw_power_vddactrl,
312 POWER_VDDACTRL_PWDN_BRNOUT);
314 setbits_le32(&power_regs->hw_power_vddioctrl,
315 POWER_VDDIOCTRL_PWDN_BRNOUT);
317 clrbits_le32(&power_regs->hw_power_vdddctrl,
318 POWER_VDDDCTRL_PWDN_BRNOUT);
320 clrbits_le32(&power_regs->hw_power_vddactrl,
321 POWER_VDDACTRL_PWDN_BRNOUT);
323 clrbits_le32(&power_regs->hw_power_vddioctrl,
324 POWER_VDDIOCTRL_PWDN_BRNOUT);
328 __static int mx28_get_vddio_power_source_off(void)
330 #ifndef CONFIG_SPL_FIXED_BATT_SUPPLY_
331 struct mx28_power_regs *power_regs =
332 (struct mx28_power_regs *)MXS_POWER_BASE;
335 dprintf("%s@%d: \n", __func__, __LINE__);
336 if (mx28_power_vdd5v_gt_vddio()) {
337 tmp = readl(&power_regs->hw_power_vddioctrl);
338 if (tmp & POWER_VDDIOCTRL_DISABLE_FET) {
339 if ((tmp & POWER_VDDIOCTRL_LINREG_OFFSET_MASK) ==
340 POWER_VDDDCTRL_LINREG_OFFSET_0STEPS) {
341 dprintf("%s@%d: 1\n", __func__, __LINE__);
346 if (!(readl(&power_regs->hw_power_5vctrl) &
347 POWER_5VCTRL_ENABLE_DCDC)) {
348 dprintf("tmp=%x mask %x = %x == %x?\n",
349 tmp, POWER_VDDIOCTRL_LINREG_OFFSET_MASK,
350 tmp & POWER_VDDIOCTRL_LINREG_OFFSET_MASK,
351 POWER_VDDDCTRL_LINREG_OFFSET_0STEPS);
352 if ((tmp & POWER_VDDIOCTRL_LINREG_OFFSET_MASK) ==
353 POWER_VDDDCTRL_LINREG_OFFSET_0STEPS) {
354 dprintf("%s@%d: 1\n", __func__, __LINE__);
357 if ((tmp & POWER_VDDIOCTRL_LINREG_OFFSET_MASK) ==
358 POWER_VDDIOCTRL_LINREG_OFFSET_1STEPS_BELOW) {
359 dprintf("%s@%d: 1\n", __func__, __LINE__);
364 dprintf("%s@%d: 0\n", __func__, __LINE__);
367 dprintf("%s@%d: 1\n", __func__, __LINE__);
372 __static int mx28_get_vddd_power_source_off(void)
374 #ifndef CONFIG_SPL_FIXED_BATT_SUPPLY_
375 struct mx28_power_regs *power_regs =
376 (struct mx28_power_regs *)MXS_POWER_BASE;
379 dprintf("%s@%d: \n", __func__, __LINE__);
380 tmp = readl(&power_regs->hw_power_vdddctrl);
381 if (tmp & POWER_VDDDCTRL_DISABLE_FET) {
382 if ((tmp & POWER_VDDDCTRL_LINREG_OFFSET_MASK) ==
383 POWER_VDDDCTRL_LINREG_OFFSET_0STEPS) {
384 dprintf("%s@%d: 1\n", __func__, __LINE__);
389 if (readl(&power_regs->hw_power_sts) & POWER_STS_VDD5V_GT_VDDIO) {
390 if (!(readl(&power_regs->hw_power_5vctrl) &
391 POWER_5VCTRL_ENABLE_DCDC)) {
392 dprintf("%s@%d: 1\n", __func__, __LINE__);
397 if ((tmp & POWER_VDDDCTRL_ENABLE_LINREG)) {
398 if ((tmp & POWER_VDDDCTRL_LINREG_OFFSET_MASK) ==
399 POWER_VDDDCTRL_LINREG_OFFSET_1STEPS_BELOW) {
400 dprintf("%s@%d: 1\n", __func__, __LINE__);
404 dprintf("%s@%d: 0\n", __func__, __LINE__);
407 dprintf("%s@%d: 1\n", __func__, __LINE__);
412 __static void mx28_power_set_vddio(uint32_t new_target, uint32_t new_brownout)
414 struct mx28_power_regs *power_regs =
415 (struct mx28_power_regs *)MXS_POWER_BASE;
416 uint32_t cur_target, diff, bo_int = 0;
417 uint32_t powered_by_linreg;
419 dprintf("%s@%d: \n", __func__, __LINE__);
420 new_brownout = (new_target - new_brownout) / 25;
421 if (new_brownout > 7) {
422 dprintf("Bad VDDD brownout offset\n");
426 cur_target = readl(&power_regs->hw_power_vddioctrl);
427 cur_target &= POWER_VDDIOCTRL_TRG_MASK;
428 cur_target *= 50; /* 50 mV step*/
429 cur_target += 2800; /* 2800 mV lowest */
431 powered_by_linreg = mx28_get_vddio_power_source_off();
432 if (new_target != cur_target)
433 dprintf("%s@%d: stepping VDDIO from %u to %u\n", __func__, __LINE__,
434 cur_target, new_target);
436 dprintf("%s@%d: VDDIO is at %u\n", __func__, __LINE__,
437 cur_target, new_target);
438 if (new_target > cur_target) {
440 if (powered_by_linreg) {
441 bo_int = readl(&power_regs->hw_power_vddioctrl);
442 clrbits_le32(&power_regs->hw_power_vddioctrl,
443 POWER_CTRL_ENIRQ_VDDIO_BO);
446 setbits_le32(&power_regs->hw_power_vddioctrl,
447 POWER_VDDIOCTRL_BO_OFFSET_MASK);
449 if (new_target - cur_target > 100)
450 diff = cur_target + 100;
457 clrsetbits_le32(&power_regs->hw_power_vddioctrl,
458 POWER_VDDIOCTRL_TRG_MASK, diff);
459 dprintf("%s@%d: vddioctrl=%x\n", __func__, __LINE__,
460 readl(&power_regs->hw_power_vddioctrl));
462 if (powered_by_linreg)
465 while (!(readl(&power_regs->hw_power_sts) &
470 dprintf("%s@%d: sts=%x\n", __func__, __LINE__,
471 readl(&power_regs->hw_power_sts));
473 cur_target = readl(&power_regs->hw_power_vddioctrl);
474 cur_target &= POWER_VDDIOCTRL_TRG_MASK;
475 cur_target *= 50; /* 50 mV step*/
476 cur_target += 2800; /* 2800 mV lowest */
477 } while (new_target > cur_target);
479 if (powered_by_linreg) {
480 writel(POWER_CTRL_VDDIO_BO_IRQ,
481 &power_regs->hw_power_ctrl_clr);
482 if (bo_int & POWER_CTRL_ENIRQ_VDDIO_BO)
483 setbits_le32(&power_regs->hw_power_vddioctrl,
484 POWER_CTRL_ENIRQ_VDDIO_BO);
485 dprintf("%s@%d: vddioctrl=%x\n", __func__, __LINE__,
486 readl(&power_regs->hw_power_vddioctrl));
488 dprintf("%s@%d: Done\n", __func__, __LINE__);
491 if (cur_target - new_target > 100)
492 diff = cur_target - 100;
499 clrsetbits_le32(&power_regs->hw_power_vddioctrl,
500 POWER_VDDIOCTRL_TRG_MASK, diff);
502 if (powered_by_linreg)
505 while (!(readl(&power_regs->hw_power_sts) &
510 dprintf("%s@%d: sts=%x\n", __func__, __LINE__,
511 readl(&power_regs->hw_power_sts));
513 cur_target = readl(&power_regs->hw_power_vddioctrl);
514 cur_target &= POWER_VDDIOCTRL_TRG_MASK;
515 cur_target *= 50; /* 50 mV step*/
516 cur_target += 2800; /* 2800 mV lowest */
517 } while (new_target < cur_target);
518 dprintf("%s@%d: Done\n", __func__, __LINE__);
521 clrsetbits_le32(&power_regs->hw_power_vddioctrl,
522 POWER_VDDDCTRL_BO_OFFSET_MASK,
523 new_brownout << POWER_VDDDCTRL_BO_OFFSET_OFFSET);
524 dprintf("%s@%d: vddioctrl=%x\n", __func__, __LINE__,
525 readl(&power_regs->hw_power_vddioctrl));
528 __static void mx28_power_set_vddd(uint32_t new_target, uint32_t new_brownout)
530 struct mx28_power_regs *power_regs =
531 (struct mx28_power_regs *)MXS_POWER_BASE;
532 uint32_t cur_target, diff, bo_int = 0;
533 uint32_t powered_by_linreg;
535 dprintf("%s@%d: \n", __func__, __LINE__);
536 new_brownout = (new_target - new_brownout) / 25;
537 if (new_brownout > 7) {
538 dprintf("Bad VDDD brownout offset\n");
541 cur_target = readl(&power_regs->hw_power_vdddctrl);
542 cur_target &= POWER_VDDDCTRL_TRG_MASK;
543 cur_target *= 25; /* 25 mV step*/
544 cur_target += 800; /* 800 mV lowest */
546 powered_by_linreg = mx28_get_vddd_power_source_off();
547 if (new_target != cur_target)
548 dprintf("%s@%d: stepping VDDD from %u to %u\n", __func__, __LINE__,
549 cur_target, new_target);
551 dprintf("%s@%d: VDDD is at %u\n", __func__, __LINE__,
552 cur_target, new_target);
553 if (new_target > cur_target) {
554 if (powered_by_linreg) {
555 bo_int = readl(&power_regs->hw_power_vdddctrl);
556 clrbits_le32(&power_regs->hw_power_vdddctrl,
557 POWER_CTRL_ENIRQ_VDDD_BO);
560 setbits_le32(&power_regs->hw_power_vdddctrl,
561 POWER_VDDDCTRL_BO_OFFSET_MASK);
564 if (new_target - cur_target > 100)
565 diff = cur_target + 100;
572 clrsetbits_le32(&power_regs->hw_power_vdddctrl,
573 POWER_VDDDCTRL_TRG_MASK, diff);
575 if (powered_by_linreg)
578 while (!(readl(&power_regs->hw_power_sts) &
583 dprintf("%s@%d: sts=%x\n", __func__, __LINE__,
584 readl(&power_regs->hw_power_sts));
586 cur_target = readl(&power_regs->hw_power_vdddctrl);
587 cur_target &= POWER_VDDDCTRL_TRG_MASK;
588 cur_target *= 25; /* 25 mV step*/
589 cur_target += 800; /* 800 mV lowest */
590 } while (new_target > cur_target);
592 if (powered_by_linreg) {
593 writel(POWER_CTRL_VDDD_BO_IRQ,
594 &power_regs->hw_power_ctrl_clr);
595 if (bo_int & POWER_CTRL_ENIRQ_VDDD_BO)
596 setbits_le32(&power_regs->hw_power_vdddctrl,
597 POWER_CTRL_ENIRQ_VDDD_BO);
599 dprintf("%s@%d: Done\n", __func__, __LINE__);
602 if (cur_target - new_target > 100)
603 diff = cur_target - 100;
610 clrsetbits_le32(&power_regs->hw_power_vdddctrl,
611 POWER_VDDDCTRL_TRG_MASK, diff);
613 if (powered_by_linreg)
616 while (!(readl(&power_regs->hw_power_sts) &
621 dprintf("%s@%d: sts=%x\n", __func__, __LINE__,
622 readl(&power_regs->hw_power_sts));
624 cur_target = readl(&power_regs->hw_power_vdddctrl);
625 cur_target &= POWER_VDDDCTRL_TRG_MASK;
626 cur_target *= 25; /* 25 mV step*/
627 cur_target += 800; /* 800 mV lowest */
628 } while (new_target < cur_target);
629 dprintf("%s@%d: Done\n", __func__, __LINE__);
632 clrsetbits_le32(&power_regs->hw_power_vdddctrl,
633 POWER_VDDDCTRL_BO_OFFSET_MASK,
634 new_brownout << POWER_VDDDCTRL_BO_OFFSET_OFFSET);
637 void mx28_power_init(void)
639 struct mx28_power_regs *power_regs =
640 (struct mx28_power_regs *)MXS_POWER_BASE;
642 dprintf("%s: %s %s\n", __func__, __DATE__, __TIME__);
643 dprintf("ctrl=%x\n", readl(&power_regs->hw_power_ctrl));
644 dprintf("sts=%x\n", readl(&power_regs->hw_power_sts));
645 #ifdef CONFIG_SPL_FIXED_BATT_SUPPLY_
646 writel(0x00018024, &power_regs->hw_power_ctrl);
647 writel(0x20100592, &power_regs->hw_power_5vctrl);
648 writel(0x00000018, &power_regs->hw_power_dcdc4p2);
649 writel(0x0061071c, &power_regs->hw_power_vdddctrl);
650 writel(0x0000270c, &power_regs->hw_power_vddactrl);
651 writel(0x0004260a, &power_regs->hw_power_vddioctrl);
653 dprintf("%s@%d\n", __func__, __LINE__);
654 mx28_power_clock2xtal();
655 dprintf("%s@%d\n", __func__, __LINE__);
656 mx28_power_clear_auto_restart();
657 dprintf("%s@%d\n", __func__, __LINE__);
658 mx28_power_set_linreg();
659 dprintf("%s@%d\n", __func__, __LINE__);
660 #ifndef CONFIG_SPL_FIXED_BATT_SUPPLY
661 mx28_power_setup_5v_detect();
662 dprintf("%s@%d\n", __func__, __LINE__);
663 mx28_power_configure_power_source();
664 // dprintf("%s@%d\n", __func__, __LINE__);
665 // mx28_enable_output_rail_protection();
666 dprintf("%s@%d\n", __func__, __LINE__);
668 mx28_power_set_vddio(3300, 3150);
669 dprintf("%s@%d\n", __func__, __LINE__);
671 mx28_power_set_vddd(1500, 1325);
672 dprintf("%s@%d\n", __func__, __LINE__);
674 writel(POWER_CTRL_VDDD_BO_IRQ | POWER_CTRL_VDDA_BO_IRQ |
675 POWER_CTRL_VDDIO_BO_IRQ | POWER_CTRL_VDD5V_DROOP_IRQ |
676 POWER_CTRL_VBUS_VALID_IRQ | POWER_CTRL_BATT_BO_IRQ |
677 POWER_CTRL_DCDC4P2_BO_IRQ, &power_regs->hw_power_ctrl_clr);
679 writel(POWER_5VCTRL_PWDN_5VBRNOUT, &power_regs->hw_power_5vctrl_set);
683 dprintf("%s@%d\n", __func__, __LINE__);
684 mx28_src_power_init();
685 dprintf("%s@%d\n", __func__, __LINE__);
686 mx28_fixed_batt_boot();
687 dprintf("%s@%d\n", __func__, __LINE__);
688 mx28_power_clock2pll();
689 dprintf("%s@%d\n", __func__, __LINE__);
691 dprintf("%s@%d\n", __func__, __LINE__);
692 mx28_switch_vddd_to_dcdc_source();
694 dprintf("%s@%d\n", __func__, __LINE__);
695 mx28_enable_output_rail_protection();
697 dprintf("%s@%d\n", __func__, __LINE__);
698 mx28_power_set_vddio(3300, 3150);
700 dprintf("%s@%d\n", __func__, __LINE__);
701 mx28_power_set_vddd(1500, 1325);
702 dprintf("%s@%d\n", __func__, __LINE__);
704 writel(POWER_CTRL_VDDD_BO_IRQ | POWER_CTRL_VDDA_BO_IRQ |
705 POWER_CTRL_VDDIO_BO_IRQ | POWER_CTRL_VDD5V_DROOP_IRQ |
706 POWER_CTRL_VBUS_VALID_IRQ | POWER_CTRL_BATT_BO_IRQ |
707 POWER_CTRL_DCDC4P2_BO_IRQ, &power_regs->hw_power_ctrl_clr);
710 dprintf("sts=%x\n", readl(&power_regs->hw_power_sts));
711 dprintf("vddioctrl=%x\n", readl(&power_regs->hw_power_vddioctrl));
712 dprintf("vdddctrl=%x\n", readl(&power_regs->hw_power_vdddctrl));
713 dprintf("5vctrl=%x\n", readl(&power_regs->hw_power_5vctrl));
714 dprintf("dcdc4p2=%x\n", readl(&power_regs->hw_power_dcdc4p2));
715 dprintf("%s@%d: Finished\n", __func__, __LINE__);
716 memdump(0x80044000, 0x60);
720 #ifdef CONFIG_SPL_MX28_PSWITCH_WAIT
721 void mx28_power_wait_pswitch(void)
723 struct mx28_power_regs *power_regs =
724 (struct mx28_power_regs *)MXS_POWER_BASE;
726 dprintf("%s@%d: \n", __func__, __LINE__);
727 while (!(readl(&power_regs->hw_power_sts) & POWER_STS_PSWITCH_MASK))