Add more stock U-Boot images
[oweals/u-boot_mod.git] / u-boot / common / cmd_custom.c
1 /*
2  * Copyright (C) 2016 Piotr Dymacz <piotr@dymacz.pl>
3  *
4  * SPDX-License-Identifier: GPL-2.0
5  */
6
7 /*
8  * Custom/miscellaneous commands
9  */
10
11 #include <common.h>
12 #include <command.h>
13 #include <asm/mipsregs.h>
14 #include <asm/addrspace.h>
15 #include <ar7240_soc.h>
16
17 /* TODO: remove extern and include header file*/
18 extern void qca_sys_clocks(u32 *cpu_clk, u32 *ddr_clk, u32 *ahb_clk,
19                                                    u32 *spi_clk, u32 *ref_clk);
20
21 #if defined(CONFIG_CMD_MAC) &&\
22     defined(OFFSET_MAC_ADDRESS)
23 /*
24  * Show MAC address(es)
25  */
26 int do_print_mac(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){
27         char buffer[6];
28 #if defined(OFFSET_MAC_ADDRESS2)
29         char buffer2[6];
30 #endif
31
32 #if defined(OFFSET_MAC_ADDRESS2)
33         // get MAC1 and MAC2 addresses from flash and print them
34         memcpy(buffer,  (void *)(CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_MAC_ADDRESS),  6);
35         memcpy(buffer2, (void *)(CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_MAC_ADDRESS2), 6);
36
37         puts("Current MAC addresses stored in FLASH:\n");
38         printf("MAC1 at 0x%X: %02X:%02X:%02X:%02X:%02X:%02X\n", CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_MAC_ADDRESS,
39                                                                                                                         buffer[0] & 0xFF, buffer[1] & 0xFF, buffer[2] & 0xFF, buffer[3] & 0xFF, buffer[4] & 0xFF, buffer[5] & 0xFF);
40
41         printf("MAC2 at 0x%X: %02X:%02X:%02X:%02X:%02X:%02X\n\n", CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_MAC_ADDRESS2,
42                                                                                                                           buffer2[0] & 0xFF, buffer2[1] & 0xFF, buffer2[2] & 0xFF, buffer2[3] & 0xFF, buffer2[4] & 0xFF, buffer2[5] & 0xFF);
43 #else
44         // get MAC address from flash and print it
45         memcpy(buffer, (void *)(CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_MAC_ADDRESS), 6);
46
47         printf("Current MAC address stored in FLASH at offset 0x%X: ", CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_MAC_ADDRESS);
48         printf("%02X:%02X:%02X:%02X:%02X:%02X\n\n", buffer[0] & 0xFF, buffer[1] & 0xFF, buffer[2] & 0xFF, buffer[3] & 0xFF, buffer[4] & 0xFF, buffer[5] & 0xFF);
49 #endif
50
51         return(0);
52 }
53
54 #if defined(OFFSET_MAC_ADDRESS2)
55 U_BOOT_CMD(printmac, 1, 1, do_print_mac, "print MAC addresses stored in FLASH\n", NULL);
56 #else
57 U_BOOT_CMD(printmac, 1, 1, do_print_mac, "print MAC address stored in FLASH\n", NULL);
58 #endif
59
60 /*
61  * Change MAC address(es)
62  */
63 int do_set_mac(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){
64         unsigned char *data_pointer;
65         char buf[128];
66         int i = 0, j = 0;
67
68         // allow only 2 arg (command name + mac), second argument length should be 17 (xx:xx:xx:xx:xx:xx)
69         if(argc != 2 || strlen(argv[1]) != 17){
70                 print_cmd_help(cmdtp);
71                 return(1);
72         }
73
74         // count ':'
75         for(i = 0; i< 17; i++){
76                 if(argv[1][i] == ':'){
77                         j++;
78                 }
79         }
80
81         if(j != 5){
82                 printf_err("given MAC address has wrong format (should be: xx:xx:xx:xx:xx:xx)!\n");
83                 return(1);
84         }
85
86         // backup block with MAC address from flash in RAM
87         data_pointer = (unsigned char *)CONFIG_LOADADDR;
88
89         if(!data_pointer){
90                 printf_err("couldn't allocate RAM for data block backup!\n");
91                 return(1);
92         }
93
94         puts("** Notice:\n   you should always make a backup of your device\n           entire FLASH content before making any changes\n\n");
95
96         memcpy((void *)data_pointer, (void *)(CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK), OFFSET_MAC_DATA_BLOCK_LENGTH);
97
98         // store new MAC address in RAM
99         for(i = 0; i < 6; i++){
100                 data_pointer[OFFSET_MAC_ADDRESS + i] = simple_strtoul((char *)(argv[1] + i*3), NULL, 16);
101         }
102
103         // now we can erase flash and write data from RAM
104         sprintf(buf,
105                         "erase 0x%lX +0x%lX; cp.b 0x%lX 0x%lX 0x%lX",
106                         CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK,
107                         OFFSET_MAC_DATA_BLOCK_LENGTH,
108                         CONFIG_LOADADDR,
109                         CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK,
110                         OFFSET_MAC_DATA_BLOCK_LENGTH);
111
112         printf("Executing: %s\n\n", buf);
113
114         return(run_command(buf, 0));
115 }
116
117 U_BOOT_CMD(setmac, 2, 0, do_set_mac, "save new MAC address in FLASH\n", "xx:xx:xx:xx:xx:xx\n\t- change MAC address stored in FLASH (xx - value in hex format)\n");
118
119 #endif /* if defined(CONFIG_CMD_MAC) && defined(OFFSET_MAC_ADDRESS) */
120
121 #if defined(OFFSET_ROUTER_MODEL)
122 /*
123  * Show TP-Link router model
124  */
125 int do_print_model(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){
126         unsigned char buffer[8];
127
128         // get router model from flash and print it
129         memcpy(buffer, (void *)(CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_ROUTER_MODEL), 8);
130
131         printf("Router model stored in FLASH at offset 0x%X: ", CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_ROUTER_MODEL);
132         printf("%02X%02X%02X%02X%02X%02X%02X%02X\n\n", buffer[0] & 0xFF, buffer[1] & 0xFF, buffer[2] & 0xFF, buffer[3] & 0xFF, buffer[4] & 0xFF, buffer[5] & 0xFF, buffer[6] & 0xFF, buffer[7] & 0xFF);
133
134         return(0);
135 }
136
137 U_BOOT_CMD(printmodel, 1, 1, do_print_model, "print router model stored in FLASH\n", NULL);
138
139 #endif /* if defined(OFFSET_ROUTER_MODEL) */
140
141 #if defined(OFFSET_PIN_NUMBER)
142 /*
143  * Show pin number
144  */
145 int do_print_pin(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){
146         unsigned char buffer[9];
147
148         // get pin number from flash and print it
149         memcpy(buffer, (void *)(CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_PIN_NUMBER), 8);
150         buffer[8] = 0;
151
152         printf("Router pin number stored in FLASH at offset 0x%X: ", CFG_FLASH_BASE + OFFSET_MAC_DATA_BLOCK + OFFSET_PIN_NUMBER);
153         printf("%s\n\n", buffer);
154
155         return(0);
156 }
157
158 U_BOOT_CMD(printpin, 1, 1, do_print_pin, "print WPS pin stored in FLASH\n", NULL);
159
160 #endif /* if defined(OFFSET_PIN_NUMBER) */
161
162 #if defined(CONFIG_NETCONSOLE)
163 /*
164  * Start NetConsole
165  */
166 int do_start_nc(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){
167         return(run_command("setenv stdin nc;setenv stdout nc;setenv stderr nc;version;", 0));
168 }
169
170 U_BOOT_CMD(startnc, 1, 0, do_start_nc, "start net console\n", NULL);
171
172 /*
173  * Start Serial Console
174  */
175 int do_start_sc(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){
176         return(run_command("setenv stdin serial;setenv stdout serial;setenv stderr serial;version;", 0));
177 }
178
179 U_BOOT_CMD(startsc, 1, 0, do_start_sc, "start serial console\n", NULL);
180
181 #endif /* if defined(CONFIG_NETCONSOLE) */
182
183 #if defined(CONFIG_CMD_ENV) && defined(CONFIG_CMD_FLASH)
184 /*
185  * Erase environment sector
186  */
187 int do_default_env(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[]){
188         int rcode = 0;
189         int len;
190         ulong end_addr, flash_sect_addr;
191 #if defined(CFG_ENV_SECT_SIZE) && (CFG_ENV_SECT_SIZE > CFG_ENV_SIZE)
192         int rc;
193         ulong flash_offset;
194         unsigned char env_buffer[CFG_ENV_SECT_SIZE];
195 #endif
196
197 #if defined(CFG_ENV_SECT_SIZE) && (CFG_ENV_SECT_SIZE > CFG_ENV_SIZE)
198         flash_offset    = CFG_ENV_ADDR & (CFG_ENV_SECT_SIZE-1);
199         flash_sect_addr = CFG_ENV_ADDR & ~(CFG_ENV_SECT_SIZE-1);
200
201         /* copy whole env sector to temporary buffer */
202         memcpy(env_buffer, (void *)flash_sect_addr, CFG_ENV_SECT_SIZE);
203
204         /* clear env part */
205         memset((uchar *)((unsigned long)env_buffer + flash_offset), 0xFF, CFG_ENV_SIZE);
206
207         len      = CFG_ENV_SECT_SIZE;
208 #else
209         flash_sect_addr = CFG_ENV_ADDR;
210         len = CFG_ENV_SIZE;
211 #endif
212
213         end_addr = flash_sect_addr + len - 1;
214
215         /* erase whole env sector */
216         if(flash_sect_erase(flash_sect_addr, end_addr)){
217                 rcode = 1;
218         }
219
220 #if defined(CFG_ENV_SECT_SIZE) && (CFG_ENV_SECT_SIZE > CFG_ENV_SIZE)
221         /* restore data from buffer in FLASH */
222         rc = flash_write((char *)env_buffer, flash_sect_addr, len);
223
224         if(rc != 0){
225                 flash_perror(rc);
226                 rcode = 1;
227         }
228 #endif
229
230         return(rcode);
231 }
232
233 U_BOOT_CMD(defenv, 1, 0, do_default_env, "reset environment variables to their default values\n", NULL);
234 #endif /* if CONFIG_CMD_ENV && CONFIG_CMD_FLASH */
235
236 /*
237  * Allows to get reset button status:
238  * - returns 0 if button is pressed
239  * - returns 1 if button is not pressed
240  *
241  * Logic here must be inverted as in shell
242  * 0 means success/true
243  *
244  * This allows to use it in scripts, ex.:
245  * if button; then ...; else ...; fi ...
246  *
247  * or, simply:
248  * button && echo pressed!
249  * button || echo not pressed!
250  */
251 #if defined(CONFIG_CMD_BUTTON) &&\
252     defined(CONFIG_GPIO_RESET_BTN)
253 int do_button(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
254 {
255 #if defined(CFG_HUSH_PARSER)
256         return !reset_button_status();
257 #else
258         int btn = reset_button_status();
259
260         if (btn)
261                 puts("Reset button is pressed\n");
262         else
263                 puts("Reset button is not pressed\n");
264
265         return !btn;
266 #endif
267 }
268
269 U_BOOT_CMD(button, 1, 1, do_button,
270         "get reset button status\n", NULL);
271 #endif /* CONFIG_CMD_BUTTON && CONFIG_GPIO_RESET_BTN */
272
273 /*
274  * Allows to delay execution
275  * for a given/specified time (in ms)
276  */
277 #if defined(CONFIG_CMD_SLEEP)
278 int do_sleep(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
279 {
280         if (argc != 2) {
281                 print_cmd_help(cmdtp);
282                 return 1;
283         }
284
285         milisecdelay(simple_strtoul(argv[1], NULL, 10));
286
287         return 0;
288 }
289
290 U_BOOT_CMD(sleep, 2, 1, do_sleep,
291         "sleep for specified time\n", "ms\n"
292         "\t- sleep for 'ms' number of milliseconds\n");
293 #endif /* CONFIG_CMD_SLEEP */
294
295 /*
296  * Turns on/off LED/s
297  */
298 #if defined(CONFIG_CMD_LED)
299 int do_ledon(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
300 {
301         all_led_on();
302
303         return 0;
304 }
305
306 int do_ledoff(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
307 {
308         all_led_off();
309
310         return 0;
311 }
312
313 U_BOOT_CMD(ledon,  1, 1, do_ledon,  "turn LED/s on\n", NULL);
314 U_BOOT_CMD(ledoff, 1, 1, do_ledoff, "turn LED/s off\n", NULL);
315 #endif /* CONFIG_CMD_LED */
316
317 /*
318  * Checks if last reset was caused by watchdog
319  */
320 #if defined(CONFIG_CMD_RSTBYWDT)
321 int do_rstbywdt(cmd_tbl_t * cmdtp, int flag, int argc, char *argv[])
322 {
323         return !last_reset_wdt();
324 }
325
326 U_BOOT_CMD(rstbywdt, 1, 1, do_rstbywdt, "check if last reset was caused by watchdog\n", NULL);
327 #endif /* CONFIG_CMD_RSTBYWDT */