Commit 76048fc705030d356183d97a54440390134e6aab

Authored by phu.luuan
Committed by Larisa Grigore
1 parent 16ee190363

mdio: Save previous status for mdio list command

When mdio list command is called, it doesn't save previous parameter.
So, when we press enter to repeat command, it doesn't show any thing.
Remove return instruction when call do_mdio with "list" parameter.

Signed-off-by: phu.luuan <phu.luuan@nxp.com>
Signed-off-by: Dan Nica <dan.nica@nxp.com>
Issue: ALB-1741

Showing 1 changed file with 5 additions and 6 deletions Inline Diff

1 // SPDX-License-Identifier: GPL-2.0+ 1 // SPDX-License-Identifier: GPL-2.0+
2 /* 2 /*
3 * (C) Copyright 2011 Freescale Semiconductor, Inc 3 * (C) Copyright 2011 Freescale Semiconductor, Inc
4 * Andy Fleming 4 * Andy Fleming
5 * Copyright 2017 NXP
5 */ 6 */
6 7
7 /* 8 /*
8 * MDIO Commands 9 * MDIO Commands
9 */ 10 */
10 11
11 #include <common.h> 12 #include <common.h>
12 #include <command.h> 13 #include <command.h>
13 #include <miiphy.h> 14 #include <miiphy.h>
14 #include <phy.h> 15 #include <phy.h>
15 16
16 static char last_op[2]; 17 static char last_op[2];
17 static uint last_data; 18 static uint last_data;
18 static uint last_addr_lo; 19 static uint last_addr_lo;
19 static uint last_addr_hi; 20 static uint last_addr_hi;
20 static uint last_devad_lo; 21 static uint last_devad_lo;
21 static uint last_devad_hi; 22 static uint last_devad_hi;
22 static uint last_reg_lo; 23 static uint last_reg_lo;
23 static uint last_reg_hi; 24 static uint last_reg_hi;
24 25
25 static int extract_range(char *input, int *plo, int *phi) 26 static int extract_range(char *input, int *plo, int *phi)
26 { 27 {
27 char *end; 28 char *end;
28 *plo = simple_strtol(input, &end, 16); 29 *plo = simple_strtol(input, &end, 16);
29 if (end == input) 30 if (end == input)
30 return -1; 31 return -1;
31 32
32 if ((*end == '-') && *(++end)) 33 if ((*end == '-') && *(++end))
33 *phi = simple_strtol(end, NULL, 16); 34 *phi = simple_strtol(end, NULL, 16);
34 else if (*end == '\0') 35 else if (*end == '\0')
35 *phi = *plo; 36 *phi = *plo;
36 else 37 else
37 return -1; 38 return -1;
38 39
39 return 0; 40 return 0;
40 } 41 }
41 42
42 static int mdio_write_ranges(struct mii_dev *bus, 43 static int mdio_write_ranges(struct mii_dev *bus,
43 int addrlo, 44 int addrlo,
44 int addrhi, int devadlo, int devadhi, 45 int addrhi, int devadlo, int devadhi,
45 int reglo, int reghi, unsigned short data, 46 int reglo, int reghi, unsigned short data,
46 int extended) 47 int extended)
47 { 48 {
48 struct phy_device *phydev; 49 struct phy_device *phydev;
49 int addr, devad, reg; 50 int addr, devad, reg;
50 int err = 0; 51 int err = 0;
51 52
52 for (addr = addrlo; addr <= addrhi; addr++) { 53 for (addr = addrlo; addr <= addrhi; addr++) {
53 phydev = bus->phymap[addr]; 54 phydev = bus->phymap[addr];
54 55
55 for (devad = devadlo; devad <= devadhi; devad++) { 56 for (devad = devadlo; devad <= devadhi; devad++) {
56 for (reg = reglo; reg <= reghi; reg++) { 57 for (reg = reglo; reg <= reghi; reg++) {
57 if (!phydev) 58 if (!phydev)
58 err = bus->write(bus, addr, devad, 59 err = bus->write(bus, addr, devad,
59 reg, data); 60 reg, data);
60 else if (!extended) 61 else if (!extended)
61 err = phy_write_mmd(phydev, devad, 62 err = phy_write_mmd(phydev, devad,
62 reg, data); 63 reg, data);
63 else 64 else
64 err = phydev->drv->writeext(phydev, 65 err = phydev->drv->writeext(phydev,
65 addr, devad, reg, data); 66 addr, devad, reg, data);
66 67
67 if (err) 68 if (err)
68 goto err_out; 69 goto err_out;
69 } 70 }
70 } 71 }
71 } 72 }
72 73
73 err_out: 74 err_out:
74 return err; 75 return err;
75 } 76 }
76 77
77 static int mdio_read_ranges(struct mii_dev *bus, 78 static int mdio_read_ranges(struct mii_dev *bus,
78 int addrlo, 79 int addrlo,
79 int addrhi, int devadlo, int devadhi, 80 int addrhi, int devadlo, int devadhi,
80 int reglo, int reghi, int extended) 81 int reglo, int reghi, int extended)
81 { 82 {
82 int addr, devad, reg; 83 int addr, devad, reg;
83 struct phy_device *phydev; 84 struct phy_device *phydev;
84 85
85 printf("Reading from bus %s\n", bus->name); 86 printf("Reading from bus %s\n", bus->name);
86 for (addr = addrlo; addr <= addrhi; addr++) { 87 for (addr = addrlo; addr <= addrhi; addr++) {
87 phydev = bus->phymap[addr]; 88 phydev = bus->phymap[addr];
88 printf("PHY at address %x:\n", addr); 89 printf("PHY at address %x:\n", addr);
89 90
90 for (devad = devadlo; devad <= devadhi; devad++) { 91 for (devad = devadlo; devad <= devadhi; devad++) {
91 for (reg = reglo; reg <= reghi; reg++) { 92 for (reg = reglo; reg <= reghi; reg++) {
92 int val; 93 int val;
93 94
94 if (!phydev) 95 if (!phydev)
95 val = bus->read(bus, addr, devad, reg); 96 val = bus->read(bus, addr, devad, reg);
96 else if (!extended) 97 else if (!extended)
97 val = phy_read_mmd(phydev, devad, reg); 98 val = phy_read_mmd(phydev, devad, reg);
98 else 99 else
99 val = phydev->drv->readext(phydev, addr, 100 val = phydev->drv->readext(phydev, addr,
100 devad, reg); 101 devad, reg);
101 102
102 if (val < 0) { 103 if (val < 0) {
103 printf("Error\n"); 104 printf("Error\n");
104 105
105 return val; 106 return val;
106 } 107 }
107 108
108 if (devad >= 0) 109 if (devad >= 0)
109 printf("%d.", devad); 110 printf("%d.", devad);
110 111
111 printf("%d - 0x%x\n", reg, val & 0xffff); 112 printf("%d - 0x%x\n", reg, val & 0xffff);
112 } 113 }
113 } 114 }
114 } 115 }
115 116
116 return 0; 117 return 0;
117 } 118 }
118 119
119 /* The register will be in the form [a[-b].]x[-y] */ 120 /* The register will be in the form [a[-b].]x[-y] */
120 static int extract_reg_range(char *input, int *devadlo, int *devadhi, 121 static int extract_reg_range(char *input, int *devadlo, int *devadhi,
121 int *reglo, int *reghi) 122 int *reglo, int *reghi)
122 { 123 {
123 char *regstr; 124 char *regstr;
124 125
125 /* use strrchr to find the last string after a '.' */ 126 /* use strrchr to find the last string after a '.' */
126 regstr = strrchr(input, '.'); 127 regstr = strrchr(input, '.');
127 128
128 /* If it exists, extract the devad(s) */ 129 /* If it exists, extract the devad(s) */
129 if (regstr) { 130 if (regstr) {
130 char devadstr[32]; 131 char devadstr[32];
131 132
132 strncpy(devadstr, input, regstr - input); 133 strncpy(devadstr, input, regstr - input);
133 devadstr[regstr - input] = '\0'; 134 devadstr[regstr - input] = '\0';
134 135
135 if (extract_range(devadstr, devadlo, devadhi)) 136 if (extract_range(devadstr, devadlo, devadhi))
136 return -1; 137 return -1;
137 138
138 regstr++; 139 regstr++;
139 } else { 140 } else {
140 /* Otherwise, we have no devad, and we just got regs */ 141 /* Otherwise, we have no devad, and we just got regs */
141 *devadlo = *devadhi = MDIO_DEVAD_NONE; 142 *devadlo = *devadhi = MDIO_DEVAD_NONE;
142 143
143 regstr = input; 144 regstr = input;
144 } 145 }
145 146
146 return extract_range(regstr, reglo, reghi); 147 return extract_range(regstr, reglo, reghi);
147 } 148 }
148 149
149 static int extract_phy_range(char *const argv[], int argc, struct mii_dev **bus, 150 static int extract_phy_range(char *const argv[], int argc, struct mii_dev **bus,
150 struct phy_device **phydev, 151 struct phy_device **phydev,
151 int *addrlo, int *addrhi) 152 int *addrlo, int *addrhi)
152 { 153 {
153 struct phy_device *dev = *phydev; 154 struct phy_device *dev = *phydev;
154 155
155 if ((argc < 1) || (argc > 2)) 156 if ((argc < 1) || (argc > 2))
156 return -1; 157 return -1;
157 158
158 /* If there are two arguments, it's busname addr */ 159 /* If there are two arguments, it's busname addr */
159 if (argc == 2) { 160 if (argc == 2) {
160 *bus = miiphy_get_dev_by_name(argv[0]); 161 *bus = miiphy_get_dev_by_name(argv[0]);
161 162
162 if (!*bus) 163 if (!*bus)
163 return -1; 164 return -1;
164 165
165 return extract_range(argv[1], addrlo, addrhi); 166 return extract_range(argv[1], addrlo, addrhi);
166 } 167 }
167 168
168 /* It must be one argument, here */ 169 /* It must be one argument, here */
169 170
170 /* 171 /*
171 * This argument can be one of two things: 172 * This argument can be one of two things:
172 * 1) Ethernet device name 173 * 1) Ethernet device name
173 * 2) Just an address (use the previously-used bus) 174 * 2) Just an address (use the previously-used bus)
174 * 175 *
175 * We check all buses for a PHY which is connected to an ethernet 176 * We check all buses for a PHY which is connected to an ethernet
176 * device by the given name. If none are found, we call 177 * device by the given name. If none are found, we call
177 * extract_range() on the string, and see if it's an address range. 178 * extract_range() on the string, and see if it's an address range.
178 */ 179 */
179 dev = mdio_phydev_for_ethname(argv[0]); 180 dev = mdio_phydev_for_ethname(argv[0]);
180 181
181 if (dev) { 182 if (dev) {
182 *addrlo = *addrhi = dev->addr; 183 *addrlo = *addrhi = dev->addr;
183 *bus = dev->bus; 184 *bus = dev->bus;
184 185
185 return 0; 186 return 0;
186 } 187 }
187 188
188 /* It's an address or nothing useful */ 189 /* It's an address or nothing useful */
189 return extract_range(argv[0], addrlo, addrhi); 190 return extract_range(argv[0], addrlo, addrhi);
190 } 191 }
191 192
192 /* ---------------------------------------------------------------- */ 193 /* ---------------------------------------------------------------- */
193 static int do_mdio(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) 194 static int do_mdio(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[])
194 { 195 {
195 char op[2]; 196 char op[2];
196 int addrlo, addrhi, reglo, reghi, devadlo, devadhi; 197 int addrlo, addrhi, reglo, reghi, devadlo, devadhi;
197 unsigned short data; 198 unsigned short data;
198 int pos = argc - 1; 199 int pos = argc - 1;
199 struct mii_dev *bus; 200 struct mii_dev *bus;
200 struct phy_device *phydev = NULL; 201 struct phy_device *phydev = NULL;
201 int extended = 0; 202 int extended = 0;
202 203
203 if (argc < 2) 204 if (argc < 2)
204 return CMD_RET_USAGE; 205 return CMD_RET_USAGE;
205 206
206 #ifdef CONFIG_DM_MDIO 207 #ifdef CONFIG_DM_MDIO
207 /* probe DM MII device before any operation so they are all accesible */ 208 /* probe DM MII device before any operation so they are all accesible */
208 dm_mdio_probe_devices(); 209 dm_mdio_probe_devices();
209 #endif 210 #endif
210 211
211 /* 212 /*
212 * We use the last specified parameters, unless new ones are 213 * We use the last specified parameters, unless new ones are
213 * entered. 214 * entered.
214 */ 215 */
215 op[0] = argv[1][0]; 216 op[0] = argv[1][0];
216 addrlo = last_addr_lo; 217 addrlo = last_addr_lo;
217 addrhi = last_addr_hi; 218 addrhi = last_addr_hi;
218 devadlo = last_devad_lo; 219 devadlo = last_devad_lo;
219 devadhi = last_devad_hi; 220 devadhi = last_devad_hi;
220 reglo = last_reg_lo; 221 reglo = last_reg_lo;
221 reghi = last_reg_hi; 222 reghi = last_reg_hi;
222 data = last_data; 223 data = last_data;
223 224
224 bus = mdio_get_current_dev(); 225 bus = mdio_get_current_dev();
225 226
226 if (flag & CMD_FLAG_REPEAT) 227 if (flag & CMD_FLAG_REPEAT)
227 op[0] = last_op[0]; 228 op[0] = last_op[0];
228 229
229 if (strlen(argv[1]) > 1) { 230 if (strlen(argv[1]) > 1) {
230 op[1] = argv[1][1]; 231 op[1] = argv[1][1];
231 if (op[1] == 'x') { 232 if (op[1] == 'x') {
232 phydev = mdio_phydev_for_ethname(argv[2]); 233 phydev = mdio_phydev_for_ethname(argv[2]);
233 234
234 if (phydev) { 235 if (phydev) {
235 addrlo = phydev->addr; 236 addrlo = phydev->addr;
236 addrhi = addrlo; 237 addrhi = addrlo;
237 bus = phydev->bus; 238 bus = phydev->bus;
238 extended = 1; 239 extended = 1;
239 } else { 240 } else {
240 return CMD_RET_FAILURE; 241 return CMD_RET_FAILURE;
241 } 242 }
242 243
243 if (!phydev->drv || 244 if (!phydev->drv ||
244 (!phydev->drv->writeext && (op[0] == 'w')) || 245 (!phydev->drv->writeext && (op[0] == 'w')) ||
245 (!phydev->drv->readext && (op[0] == 'r'))) { 246 (!phydev->drv->readext && (op[0] == 'r'))) {
246 puts("PHY does not have extended functions\n"); 247 puts("PHY does not have extended functions\n");
247 return CMD_RET_FAILURE; 248 return CMD_RET_FAILURE;
248 } 249 }
249 } 250 }
250 } 251 }
251 252
252 switch (op[0]) { 253 switch (op[0]) {
253 case 'w': 254 case 'w':
254 if (pos > 1) 255 if (pos > 1)
255 data = simple_strtoul(argv[pos--], NULL, 16); 256 data = simple_strtoul(argv[pos--], NULL, 16);
256 /* Intentional fall-through - Get reg for read and write */ 257 /* Intentional fall-through - Get reg for read and write */
257 case 'r': 258 case 'r':
258 if (pos > 1) 259 if (pos > 1)
259 if (extract_reg_range(argv[pos--], &devadlo, &devadhi, 260 if (extract_reg_range(argv[pos--], &devadlo, &devadhi,
260 &reglo, &reghi)) 261 &reglo, &reghi))
261 return CMD_RET_FAILURE; 262 return CMD_RET_FAILURE;
262 /* Intentional fall-through - Get phy for all commands */ 263 /* Intentional fall-through - Get phy for all commands */
263 default: 264 default:
264 if (pos > 1) 265 if (pos > 1)
265 if (extract_phy_range(&argv[2], pos - 1, &bus, 266 if (extract_phy_range(&argv[2], pos - 1, &bus,
266 &phydev, &addrlo, &addrhi)) 267 &phydev, &addrlo, &addrhi))
267 return CMD_RET_FAILURE; 268 return CMD_RET_FAILURE;
268 269
269 break; 270 break;
270 } 271 }
271 272
272 if (!bus) { 273 if (!bus) {
273 puts("No MDIO bus found\n"); 274 puts("No MDIO bus found\n");
274 return CMD_RET_FAILURE; 275 return CMD_RET_FAILURE;
275 } 276 }
276 277
277 if (op[0] == 'l') {
278 mdio_list_devices();
279
280 return 0;
281 }
282
283 /* Save the chosen bus */ 278 /* Save the chosen bus */
284 miiphy_set_current_dev(bus->name); 279 miiphy_set_current_dev(bus->name);
285 280
286 switch (op[0]) { 281 switch (op[0]) {
287 case 'w': 282 case 'w':
288 mdio_write_ranges(bus, addrlo, addrhi, devadlo, devadhi, 283 mdio_write_ranges(bus, addrlo, addrhi, devadlo, devadhi,
289 reglo, reghi, data, extended); 284 reglo, reghi, data, extended);
290 break; 285 break;
291 286
292 case 'r': 287 case 'r':
293 mdio_read_ranges(bus, addrlo, addrhi, devadlo, devadhi, 288 mdio_read_ranges(bus, addrlo, addrhi, devadlo, devadhi,
294 reglo, reghi, extended); 289 reglo, reghi, extended);
290 break;
291
292 case 'l':
293 mdio_list_devices();
295 break; 294 break;
296 } 295 }
297 296
298 /* 297 /*
299 * Save the parameters for repeats. 298 * Save the parameters for repeats.
300 */ 299 */
301 last_op[0] = op[0]; 300 last_op[0] = op[0];
302 last_addr_lo = addrlo; 301 last_addr_lo = addrlo;
303 last_addr_hi = addrhi; 302 last_addr_hi = addrhi;
304 last_devad_lo = devadlo; 303 last_devad_lo = devadlo;
305 last_devad_hi = devadhi; 304 last_devad_hi = devadhi;
306 last_reg_lo = reglo; 305 last_reg_lo = reglo;
307 last_reg_hi = reghi; 306 last_reg_hi = reghi;
308 last_data = data; 307 last_data = data;
309 308
310 return 0; 309 return 0;
311 } 310 }
312 311
313 /***************************************************/ 312 /***************************************************/
314 313
315 U_BOOT_CMD( 314 U_BOOT_CMD(
316 mdio, 6, 1, do_mdio, 315 mdio, 6, 1, do_mdio,
317 "MDIO utility commands", 316 "MDIO utility commands",
318 "list - List MDIO buses\n" 317 "list - List MDIO buses\n"
319 "mdio read <phydev> [<devad>.]<reg> - " 318 "mdio read <phydev> [<devad>.]<reg> - "
320 "read PHY's register at <devad>.<reg>\n" 319 "read PHY's register at <devad>.<reg>\n"
321 "mdio write <phydev> [<devad>.]<reg> <data> - " 320 "mdio write <phydev> [<devad>.]<reg> <data> - "
322 "write PHY's register at <devad>.<reg>\n" 321 "write PHY's register at <devad>.<reg>\n"
323 "mdio rx <phydev> [<devad>.]<reg> - " 322 "mdio rx <phydev> [<devad>.]<reg> - "
324 "read PHY's extended register at <devad>.<reg>\n" 323 "read PHY's extended register at <devad>.<reg>\n"
325 "mdio wx <phydev> [<devad>.]<reg> <data> - " 324 "mdio wx <phydev> [<devad>.]<reg> <data> - "
326 "write PHY's extended register at <devad>.<reg>\n" 325 "write PHY's extended register at <devad>.<reg>\n"
327 "<phydev> may be:\n" 326 "<phydev> may be:\n"
328 " <busname> <addr>\n" 327 " <busname> <addr>\n"