1*4882a593Smuzhiyun /*
2*4882a593Smuzhiyun * Bluegiga APX4 Development Kit
3*4882a593Smuzhiyun *
4*4882a593Smuzhiyun * Copyright (C) 2012 Bluegiga Technologies Oy
5*4882a593Smuzhiyun *
6*4882a593Smuzhiyun * Authors:
7*4882a593Smuzhiyun * Veli-Pekka Peltola <veli-pekka.peltola@bluegiga.com>
8*4882a593Smuzhiyun * Lauri Hintsala <lauri.hintsala@bluegiga.com>
9*4882a593Smuzhiyun *
10*4882a593Smuzhiyun * Based on m28evk.c:
11*4882a593Smuzhiyun * Copyright (C) 2011 Marek Vasut <marek.vasut@gmail.com>
12*4882a593Smuzhiyun * on behalf of DENX Software Engineering GmbH
13*4882a593Smuzhiyun *
14*4882a593Smuzhiyun * SPDX-License-Identifier: GPL-2.0+
15*4882a593Smuzhiyun */
16*4882a593Smuzhiyun
17*4882a593Smuzhiyun #include <common.h>
18*4882a593Smuzhiyun #include <asm/gpio.h>
19*4882a593Smuzhiyun #include <asm/io.h>
20*4882a593Smuzhiyun #include <asm/setup.h>
21*4882a593Smuzhiyun #include <asm/arch/imx-regs.h>
22*4882a593Smuzhiyun #include <asm/arch/iomux-mx28.h>
23*4882a593Smuzhiyun #include <asm/arch/clock.h>
24*4882a593Smuzhiyun #include <asm/arch/sys_proto.h>
25*4882a593Smuzhiyun #include <linux/mii.h>
26*4882a593Smuzhiyun #include <miiphy.h>
27*4882a593Smuzhiyun #include <netdev.h>
28*4882a593Smuzhiyun #include <errno.h>
29*4882a593Smuzhiyun
30*4882a593Smuzhiyun DECLARE_GLOBAL_DATA_PTR;
31*4882a593Smuzhiyun
32*4882a593Smuzhiyun /* Functions */
board_early_init_f(void)33*4882a593Smuzhiyun int board_early_init_f(void)
34*4882a593Smuzhiyun {
35*4882a593Smuzhiyun /* IO0 clock at 480MHz */
36*4882a593Smuzhiyun mxs_set_ioclk(MXC_IOCLK0, 480000);
37*4882a593Smuzhiyun /* IO1 clock at 480MHz */
38*4882a593Smuzhiyun mxs_set_ioclk(MXC_IOCLK1, 480000);
39*4882a593Smuzhiyun
40*4882a593Smuzhiyun /* SSP0 clock at 96MHz */
41*4882a593Smuzhiyun mxs_set_sspclk(MXC_SSPCLK0, 96000, 0);
42*4882a593Smuzhiyun
43*4882a593Smuzhiyun return 0;
44*4882a593Smuzhiyun }
45*4882a593Smuzhiyun
dram_init(void)46*4882a593Smuzhiyun int dram_init(void)
47*4882a593Smuzhiyun {
48*4882a593Smuzhiyun return mxs_dram_init();
49*4882a593Smuzhiyun }
50*4882a593Smuzhiyun
board_init(void)51*4882a593Smuzhiyun int board_init(void)
52*4882a593Smuzhiyun {
53*4882a593Smuzhiyun /* Adress of boot parameters */
54*4882a593Smuzhiyun gd->bd->bi_boot_params = PHYS_SDRAM_1 + 0x100;
55*4882a593Smuzhiyun
56*4882a593Smuzhiyun return 0;
57*4882a593Smuzhiyun }
58*4882a593Smuzhiyun
59*4882a593Smuzhiyun #ifdef CONFIG_CMD_MMC
board_mmc_init(bd_t * bis)60*4882a593Smuzhiyun int board_mmc_init(bd_t *bis)
61*4882a593Smuzhiyun {
62*4882a593Smuzhiyun return mxsmmc_initialize(bis, 0, NULL, NULL);
63*4882a593Smuzhiyun }
64*4882a593Smuzhiyun #endif
65*4882a593Smuzhiyun
66*4882a593Smuzhiyun
67*4882a593Smuzhiyun #ifdef CONFIG_CMD_NET
68*4882a593Smuzhiyun
69*4882a593Smuzhiyun #define MII_PHY_CTRL2 0x1f
fecmxc_mii_postcall(int phy)70*4882a593Smuzhiyun int fecmxc_mii_postcall(int phy)
71*4882a593Smuzhiyun {
72*4882a593Smuzhiyun /* change PHY RMII clock to 50MHz */
73*4882a593Smuzhiyun miiphy_write("FEC", 0, MII_PHY_CTRL2, 0x8180);
74*4882a593Smuzhiyun
75*4882a593Smuzhiyun return 0;
76*4882a593Smuzhiyun }
77*4882a593Smuzhiyun
board_eth_init(bd_t * bis)78*4882a593Smuzhiyun int board_eth_init(bd_t *bis)
79*4882a593Smuzhiyun {
80*4882a593Smuzhiyun int ret;
81*4882a593Smuzhiyun struct eth_device *dev;
82*4882a593Smuzhiyun
83*4882a593Smuzhiyun ret = cpu_eth_init(bis);
84*4882a593Smuzhiyun if (ret) {
85*4882a593Smuzhiyun printf("FEC MXS: Unable to init FEC clocks\n");
86*4882a593Smuzhiyun return ret;
87*4882a593Smuzhiyun }
88*4882a593Smuzhiyun
89*4882a593Smuzhiyun ret = fecmxc_initialize(bis);
90*4882a593Smuzhiyun if (ret) {
91*4882a593Smuzhiyun printf("FEC MXS: Unable to init FEC\n");
92*4882a593Smuzhiyun return ret;
93*4882a593Smuzhiyun }
94*4882a593Smuzhiyun
95*4882a593Smuzhiyun dev = eth_get_dev_by_name("FEC");
96*4882a593Smuzhiyun if (!dev) {
97*4882a593Smuzhiyun printf("FEC MXS: Unable to get FEC device entry\n");
98*4882a593Smuzhiyun return -EINVAL;
99*4882a593Smuzhiyun }
100*4882a593Smuzhiyun
101*4882a593Smuzhiyun ret = fecmxc_register_mii_postcall(dev, fecmxc_mii_postcall);
102*4882a593Smuzhiyun if (ret) {
103*4882a593Smuzhiyun printf("FEC MXS: Unable to register FEC MII postcall\n");
104*4882a593Smuzhiyun return ret;
105*4882a593Smuzhiyun }
106*4882a593Smuzhiyun
107*4882a593Smuzhiyun return ret;
108*4882a593Smuzhiyun }
109*4882a593Smuzhiyun #endif
110*4882a593Smuzhiyun
111*4882a593Smuzhiyun #ifdef CONFIG_SERIAL_TAG
112*4882a593Smuzhiyun #define MXS_OCOTP_MAX_TIMEOUT 1000000
get_board_serial(struct tag_serialnr * serialnr)113*4882a593Smuzhiyun void get_board_serial(struct tag_serialnr *serialnr)
114*4882a593Smuzhiyun {
115*4882a593Smuzhiyun struct mxs_ocotp_regs *ocotp_regs =
116*4882a593Smuzhiyun (struct mxs_ocotp_regs *)MXS_OCOTP_BASE;
117*4882a593Smuzhiyun
118*4882a593Smuzhiyun serialnr->high = 0;
119*4882a593Smuzhiyun serialnr->low = 0;
120*4882a593Smuzhiyun
121*4882a593Smuzhiyun writel(OCOTP_CTRL_RD_BANK_OPEN, &ocotp_regs->hw_ocotp_ctrl_set);
122*4882a593Smuzhiyun
123*4882a593Smuzhiyun if (mxs_wait_mask_clr(&ocotp_regs->hw_ocotp_ctrl_reg, OCOTP_CTRL_BUSY,
124*4882a593Smuzhiyun MXS_OCOTP_MAX_TIMEOUT)) {
125*4882a593Smuzhiyun printf("MXS: Can't get serial number from OCOTP\n");
126*4882a593Smuzhiyun return;
127*4882a593Smuzhiyun }
128*4882a593Smuzhiyun
129*4882a593Smuzhiyun serialnr->low = readl(&ocotp_regs->hw_ocotp_cust3);
130*4882a593Smuzhiyun }
131*4882a593Smuzhiyun #endif
132*4882a593Smuzhiyun
133*4882a593Smuzhiyun #ifdef CONFIG_REVISION_TAG
get_board_rev(void)134*4882a593Smuzhiyun u32 get_board_rev(void)
135*4882a593Smuzhiyun {
136*4882a593Smuzhiyun if (env_get("revision#") != NULL)
137*4882a593Smuzhiyun return simple_strtoul(env_get("revision#"), NULL, 10);
138*4882a593Smuzhiyun return 0;
139*4882a593Smuzhiyun }
140*4882a593Smuzhiyun #endif
141