]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - arch/arm/cpu/armv7/uniphier/board_late_init.c
Merge branch 'u-boot-marvell/master' into 'u-boot-arm/master'
[karo-tx-uboot.git] / arch / arm / cpu / armv7 / uniphier / board_late_init.c
1 /*
2  * Copyright (C) 2014 Panasonic Corporation
3  *   Author: Masahiro Yamada <yamada.m@jp.panasonic.com>
4  *
5  * SPDX-License-Identifier:     GPL-2.0+
6  */
7
8 #include <common.h>
9 #include <spl.h>
10 #include <nand.h>
11 #include <asm/io.h>
12 #include <../drivers/mtd/nand/denali.h>
13
14 static void nand_denali_wp_disable(void)
15 {
16 #ifdef CONFIG_NAND_DENALI
17         /*
18          * Since the boot rom enables the write protection for NAND boot mode,
19          * it must be disabled somewhere for "nand write", "nand erase", etc.
20          * The workaround is here to not disturb the Denali NAND controller
21          * driver just for a really SoC-specific thing.
22          */
23         void __iomem *denali_reg = (void __iomem *)CONFIG_SYS_NAND_REGS_BASE;
24
25         writel(WRITE_PROTECT__FLAG, denali_reg + WRITE_PROTECT);
26 #endif
27 }
28
29 static void nand_denali_fixup(void)
30 {
31 #if defined(CONFIG_NAND_DENALI) && \
32         (defined(CONFIG_MACH_PH1_SLD8) || defined(CONFIG_MACH_PH1_PRO4))
33         /*
34          * The Denali NAND controller on some of UniPhier SoCs does not
35          * automatically query the device parameters.  For those SoCs,
36          * some registers must be set after the device is probed.
37          */
38         void __iomem *denali_reg = (void __iomem *)CONFIG_SYS_NAND_REGS_BASE;
39         struct mtd_info *mtd;
40         struct nand_chip *chip;
41
42         if (nand_curr_device < 0 ||
43             nand_curr_device >= CONFIG_SYS_MAX_NAND_DEVICE) {
44                 /* NAND was not detected. Just return. */
45                 return;
46         }
47
48         mtd = &nand_info[nand_curr_device];
49         chip = mtd->priv;
50
51         writel(mtd->erasesize / mtd->writesize, denali_reg + PAGES_PER_BLOCK);
52         writel(0, denali_reg + DEVICE_WIDTH);
53         writel(mtd->writesize, denali_reg + DEVICE_MAIN_AREA_SIZE);
54         writel(mtd->oobsize, denali_reg + DEVICE_SPARE_AREA_SIZE);
55         writel(1, denali_reg + DEVICES_CONNECTED);
56
57         /*
58          * chip->scan_bbt in nand_scan_tail() has been skipped.
59          * It should be done in here.
60          */
61         chip->scan_bbt(mtd);
62 #endif
63 }
64
65 int board_late_init(void)
66 {
67         puts("MODE:  ");
68
69         switch (spl_boot_device()) {
70         case BOOT_DEVICE_MMC1:
71                 printf("eMMC Boot\n");
72                 setenv("bootmode", "emmcboot");
73                 nand_denali_fixup();
74                 break;
75         case BOOT_DEVICE_NAND:
76                 printf("NAND Boot\n");
77                 setenv("bootmode", "nandboot");
78                 nand_denali_wp_disable();
79                 break;
80         case BOOT_DEVICE_NOR:
81                 printf("NOR Boot\n");
82                 setenv("bootmode", "norboot");
83                 nand_denali_fixup();
84                 break;
85         default:
86                 printf("Unsupported Boot Mode\n");
87                 return -1;
88         }
89
90         return 0;
91 }