1 // SPDX-License-Identifier: GPL-2.0+
2 /*
3  * Copyright 2021 Gateworks Corporation
4  */
5 
6 #include <fdt_support.h>
7 #include <init.h>
8 #include <led.h>
9 #include <miiphy.h>
10 #include <asm/arch/clock.h>
11 #include <asm/arch/sys_proto.h>
12 
13 #include "eeprom.h"
14 
board_phys_sdram_size(phys_size_t * size)15 int board_phys_sdram_size(phys_size_t *size)
16 {
17 	if (!size)
18 		return -EINVAL;
19 
20 	*size = get_ram_size((void *)PHYS_SDRAM, PHYS_SDRAM_SIZE);
21 
22 	return 0;
23 }
24 
board_fit_config_name_match(const char * name)25 int board_fit_config_name_match(const char *name)
26 {
27 	int i  = 0;
28 	const char *dtb;
29 	static char init;
30 	char buf[32];
31 
32 	do {
33 		dtb = eeprom_get_dtb_name(i++, buf, sizeof(buf));
34 		if (!strcmp(dtb, name)) {
35 			if (!init++)
36 				printf("DTB     : %s\n", name);
37 			return 0;
38 		}
39 	} while (dtb);
40 
41 	return -1;
42 }
43 
setup_fec(void)44 static int __maybe_unused setup_fec(void)
45 {
46 	struct iomuxc_gpr_base_regs *gpr =
47 		(struct iomuxc_gpr_base_regs *)IOMUXC_GPR_BASE_ADDR;
48 
49 #ifndef CONFIG_IMX8MP
50 	/* Use 125M anatop REF_CLK1 for ENET1, not from external */
51 	clrsetbits_le32(&gpr->gpr[1], 0x2000, 0);
52 #else
53 	/* Enable RGMII TX clk output */
54 	setbits_le32(&gpr->gpr[1], BIT(22));
55 #endif
56 
57 	return 0;
58 }
59 
60 #if (IS_ENABLED(CONFIG_NET))
board_phy_config(struct phy_device * phydev)61 int board_phy_config(struct phy_device *phydev)
62 {
63 	unsigned short val;
64 
65 	switch (phydev->phy_id) {
66 	case 0x2000a231: /* TI DP83867 GbE PHY */
67 		puts("DP83867 ");
68 		/* LED configuration */
69 		val = 0;
70 		val |= 0x5 << 4; /* LED1(Amber;Speed)   : 1000BT link */
71 		val |= 0xb << 8; /* LED2(Green;Link/Act): blink for TX/RX act */
72 		phy_write(phydev, MDIO_DEVAD_NONE, 24, val);
73 		break;
74 	}
75 
76 	if (phydev->drv->config)
77 		phydev->drv->config(phydev);
78 
79 	return 0;
80 }
81 #endif // IS_ENABLED(CONFIG_NET)
82 
board_init(void)83 int board_init(void)
84 {
85 	venice_eeprom_init(1);
86 
87 	if (IS_ENABLED(CONFIG_FEC_MXC))
88 		setup_fec();
89 
90 	return 0;
91 }
92 
board_late_init(void)93 int board_late_init(void)
94 {
95 	const char *str;
96 	char env[32];
97 	int ret, i;
98 	u8 enetaddr[6];
99 	char fdt[64];
100 
101 	/* Set board serial/model */
102 	if (!env_get("serial#"))
103 		env_set_ulong("serial#", eeprom_get_serial());
104 	env_set("model", eeprom_get_model());
105 
106 	/* Set fdt_file vars */
107 	i = 0;
108 	do {
109 		str = eeprom_get_dtb_name(i, fdt, sizeof(fdt));
110 		if (str) {
111 			sprintf(env, "fdt_file%d", i + 1);
112 			strcat(fdt, ".dtb");
113 			env_set(env, fdt);
114 		}
115 		i++;
116 	} while (str);
117 
118 	/* Set mac addrs */
119 	i = 0;
120 	do {
121 		if (i)
122 			sprintf(env, "eth%daddr", i);
123 		else
124 			sprintf(env, "ethaddr");
125 		str = env_get(env);
126 		if (!str) {
127 			ret = eeprom_getmac(i, enetaddr);
128 			if (!ret)
129 				eth_env_set_enetaddr(env, enetaddr);
130 		}
131 		i++;
132 	} while (!ret);
133 
134 	return 0;
135 }
136 
board_mmc_get_env_dev(int devno)137 int board_mmc_get_env_dev(int devno)
138 {
139 	return devno;
140 }
141 
ft_board_setup(void * fdt,struct bd_info * bd)142 int ft_board_setup(void *fdt, struct bd_info *bd)
143 {
144 	const char *base_model = eeprom_get_baseboard_model();
145 	char pcbrev;
146 	int off;
147 
148 	/* set board model dt prop */
149 	fdt_setprop_string(fdt, 0, "board", eeprom_get_model());
150 
151 	if (!strncmp(base_model, "GW73", 4)) {
152 		pcbrev = get_pcb_rev(base_model);
153 
154 		if (pcbrev > 'B') {
155 			printf("adjusting dt for %s\n", base_model);
156 
157 			/*
158 			 * revC replaced PCIe 5-port switch with 4-port
159 			 * which changed ethernet1 PCIe GbE
160 			 * from: pcie@0,0/pcie@1,0/pcie@2,4/pcie@6.0
161 			 *   to: pcie@0,0/pcie@1,0/pcie@2,3/pcie@5.0
162 			 */
163 			off = fdt_path_offset(fdt, "ethernet1");
164 			if (off > 0) {
165 				u32 reg[5];
166 
167 				fdt_set_name(fdt, off, "pcie@5,0");
168 				off = fdt_parent_offset(fdt, off);
169 				fdt_set_name(fdt, off, "pcie@2,3");
170 				memset(reg, 0, sizeof(reg));
171 				reg[0] = cpu_to_fdt32(PCI_DEVFN(3, 0));
172 				fdt_setprop(fdt, off, "reg", reg, sizeof(reg));
173 			}
174 		}
175 	}
176 
177 	return 0;
178 }
179