Blame view
cmd/nvedit.c
32.4 KB
83d290c56
|
1 |
// SPDX-License-Identifier: GPL-2.0+ |
a68d3ed0a
|
2 |
/* |
ea009d474
|
3 |
* (C) Copyright 2000-2013 |
a68d3ed0a
|
4 5 6 7 |
* Wolfgang Denk, DENX Software Engineering, wd@denx.de. * * (C) Copyright 2001 Sysgo Real-Time Solutions, GmbH <www.elinos.com> * Andreas Heppel <aheppel@sysgo.de> |
a000b7950
|
8 9 |
* * Copyright 2011 Freescale Semiconductor, Inc. |
a68d3ed0a
|
10 |
*/ |
ea882baf9
|
11 |
/* |
a68d3ed0a
|
12 13 |
* Support for persistent environment data * |
ea882baf9
|
14 15 |
* The "environment" is stored on external storage as a list of '\0' * terminated "name=value" strings. The end of the list is marked by |
fc0b5948e
|
16 |
* a double '\0'. The environment is preceded by a 32 bit CRC over |
ea882baf9
|
17 18 |
* the data part and, in case of redundant environment, a byte of * flags. |
a68d3ed0a
|
19 |
* |
ea882baf9
|
20 21 22 |
* This linearized representation will also be used before * relocation, i. e. as long as we don't have a full C runtime * environment. After that, we use a hash table. |
a68d3ed0a
|
23 24 25 |
*/ #include <common.h> |
18d66533a
|
26 |
#include <cli.h> |
a68d3ed0a
|
27 |
#include <command.h> |
24b852a7a
|
28 |
#include <console.h> |
a68d3ed0a
|
29 |
#include <environment.h> |
ea882baf9
|
30 31 |
#include <search.h> #include <errno.h> |
246c69225
|
32 |
#include <malloc.h> |
0eb25b619
|
33 |
#include <mapmem.h> |
2a3cb0207
|
34 |
#include <watchdog.h> |
a68d3ed0a
|
35 36 |
#include <linux/stddef.h> #include <asm/byteorder.h> |
fd37dac9e
|
37 |
#include <asm/io.h> |
a68d3ed0a
|
38 |
|
d87080b72
|
39 |
DECLARE_GLOBAL_DATA_PTR; |
f3c615b8a
|
40 41 |
#if !defined(CONFIG_ENV_IS_IN_EEPROM) && \ !defined(CONFIG_ENV_IS_IN_FLASH) && \ |
f3c615b8a
|
42 |
!defined(CONFIG_ENV_IS_IN_MMC) && \ |
57210c7cc
|
43 |
!defined(CONFIG_ENV_IS_IN_FAT) && \ |
fd1000b9c
|
44 |
!defined(CONFIG_ENV_IS_IN_EXT4) && \ |
f3c615b8a
|
45 46 47 |
!defined(CONFIG_ENV_IS_IN_NAND) && \ !defined(CONFIG_ENV_IS_IN_NVRAM) && \ !defined(CONFIG_ENV_IS_IN_ONENAND) && \ |
125d193c4
|
48 |
!defined(CONFIG_ENV_IS_IN_SATA) && \ |
f3c615b8a
|
49 |
!defined(CONFIG_ENV_IS_IN_SPI_FLASH) && \ |
0a85a9e70
|
50 |
!defined(CONFIG_ENV_IS_IN_REMOTE) && \ |
2b74433f3
|
51 |
!defined(CONFIG_ENV_IS_IN_UBI) && \ |
f3c615b8a
|
52 |
!defined(CONFIG_ENV_IS_NOWHERE) |
7b7341d7f
|
53 |
# error Define one of CONFIG_ENV_IS_IN_{EEPROM|FLASH|MMC|FAT|EXT4|\ |
d1b88cd32
|
54 |
NAND|NVRAM|ONENAND|SATA|SPI_FLASH|REMOTE|UBI} or CONFIG_ENV_IS_NOWHERE |
a68d3ed0a
|
55 |
#endif |
ea882baf9
|
56 57 58 59 |
/* * Maximum expected input data size for import command */ #define MAX_ENV_SIZE (1 << 20) /* 1 MiB */ |
a68d3ed0a
|
60 |
|
a68d3ed0a
|
61 |
/* |
ea882baf9
|
62 |
* This variable is incremented on each do_env_set(), so it can |
da95427ce
|
63 64 65 66 67 |
* be used via get_env_id() as an indication, if the environment * has changed or not. So it is possible to reread an environment * variable only if the environment was changed ... done so for * example in NetInitLoop() */ |
2f70c49e5
|
68 |
static int env_id = 1; |
a68d3ed0a
|
69 |
|
f3c615b8a
|
70 |
int get_env_id(void) |
2f70c49e5
|
71 72 73 |
{ return env_id; } |
a68d3ed0a
|
74 |
|
7ac2fe2da
|
75 |
#ifndef CONFIG_SPL_BUILD |
4c94f6c54
|
76 |
/* |
ea882baf9
|
77 78 79 |
* Command interface: print one or all environment variables * * Returns 0 in case of error, or length of printed string |
4c94f6c54
|
80 |
*/ |
be11235ab
|
81 |
static int env_print(char *name, int flag) |
a68d3ed0a
|
82 |
{ |
ea882baf9
|
83 |
char *res = NULL; |
22a4a6c5c
|
84 |
ssize_t len; |
ea882baf9
|
85 86 87 88 89 90 |
if (name) { /* print a single name */ ENTRY e, *ep; e.key = name; e.data = NULL; |
be11235ab
|
91 |
hsearch_r(e, FIND, &ep, &env_htab, flag); |
ea882baf9
|
92 93 |
if (ep == NULL) return 0; |
f3c615b8a
|
94 95 |
len = printf("%s=%s ", ep->key, ep->data); |
ea882baf9
|
96 97 |
return len; } |
a68d3ed0a
|
98 |
|
ea882baf9
|
99 |
/* print whole list */ |
be11235ab
|
100 101 |
len = hexport_r(&env_htab, ' ', flag, &res, 0, 0, NULL); |
a68d3ed0a
|
102 |
|
ea882baf9
|
103 104 105 106 |
if (len > 0) { puts(res); free(res); return len; |
a68d3ed0a
|
107 |
} |
ea882baf9
|
108 |
/* should never happen */ |
22a4a6c5c
|
109 110 |
printf("## Error: cannot export environment "); |
ea882baf9
|
111 |
return 0; |
4c94f6c54
|
112 |
} |
a68d3ed0a
|
113 |
|
088f1b199
|
114 115 |
static int do_env_print(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
4c94f6c54
|
116 117 118 |
{ int i; int rcode = 0; |
be11235ab
|
119 |
int env_flag = H_HIDE_DOT; |
49d81fdfb
|
120 121 122 123 |
#if defined(CONFIG_CMD_NVEDIT_EFI) if (argc > 1 && argv[1][0] == '-' && argv[1][1] == 'e') return do_env_print_efi(cmdtp, flag, --argc, ++argv); #endif |
be11235ab
|
124 125 126 127 128 |
if (argc > 1 && argv[1][0] == '-' && argv[1][1] == 'a') { argc--; argv++; env_flag &= ~H_HIDE_DOT; } |
a68d3ed0a
|
129 |
|
4c94f6c54
|
130 131 |
if (argc == 1) { /* print all env vars */ |
be11235ab
|
132 |
rcode = env_print(NULL, env_flag); |
ea882baf9
|
133 |
if (!rcode) |
4c94f6c54
|
134 135 136 137 138 139 140 |
return 1; printf(" Environment size: %d/%ld bytes ", rcode, (ulong)ENV_SIZE); return 0; } |
a68d3ed0a
|
141 |
|
4c94f6c54
|
142 |
/* print selected env vars */ |
be11235ab
|
143 |
env_flag &= ~H_HIDE_DOT; |
4c94f6c54
|
144 |
for (i = 1; i < argc; ++i) { |
be11235ab
|
145 |
int rc = env_print(argv[i], env_flag); |
ea882baf9
|
146 147 148 |
if (!rc) { printf("## Error: \"%s\" not defined ", argv[i]); |
4c94f6c54
|
149 |
++rcode; |
a68d3ed0a
|
150 151 |
} } |
4c94f6c54
|
152 |
|
a68d3ed0a
|
153 154 |
return rcode; } |
a000b7950
|
155 |
#ifdef CONFIG_CMD_GREPENV |
d09b1787a
|
156 157 |
static int do_env_grep(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
a000b7950
|
158 |
{ |
5a31ea04c
|
159 |
char *res = NULL; |
be29df6a1
|
160 |
int len, grep_how, grep_what; |
a000b7950
|
161 162 |
if (argc < 2) |
4c12eeb8b
|
163 |
return CMD_RET_USAGE; |
a000b7950
|
164 |
|
be29df6a1
|
165 166 |
grep_how = H_MATCH_SUBSTR; /* default: substring search */ grep_what = H_MATCH_BOTH; /* default: grep names and values */ |
d87244d5a
|
167 |
|
9a8323311
|
168 169 |
while (--argc > 0 && **++argv == '-') { char *arg = *argv; |
d87244d5a
|
170 171 |
while (*++arg) { switch (*arg) { |
be29df6a1
|
172 173 174 175 176 |
#ifdef CONFIG_REGEX case 'e': /* use regex matching */ grep_how = H_MATCH_REGEX; break; #endif |
d87244d5a
|
177 |
case 'n': /* grep for name */ |
be29df6a1
|
178 |
grep_what = H_MATCH_KEY; |
d87244d5a
|
179 180 |
break; case 'v': /* grep for value */ |
be29df6a1
|
181 |
grep_what = H_MATCH_DATA; |
d87244d5a
|
182 183 |
break; case 'b': /* grep for both */ |
be29df6a1
|
184 |
grep_what = H_MATCH_BOTH; |
d87244d5a
|
185 186 187 188 189 190 191 192 193 194 |
break; case '-': goto DONE; default: return CMD_RET_USAGE; } } } DONE: |
5a31ea04c
|
195 196 |
len = hexport_r(&env_htab, ' ', |
be29df6a1
|
197 |
flag | grep_what | grep_how, |
5a31ea04c
|
198 |
&res, 0, argc, argv); |
a000b7950
|
199 |
|
5a31ea04c
|
200 201 202 |
if (len > 0) { puts(res); free(res); |
a000b7950
|
203 |
} |
5a31ea04c
|
204 205 206 207 |
if (len < 2) return 1; return 0; |
a000b7950
|
208 209 |
} #endif |
7ac2fe2da
|
210 |
#endif /* CONFIG_SPL_BUILD */ |
a000b7950
|
211 |
|
ea882baf9
|
212 |
/* |
c3f652585
|
213 214 |
* Set a new environment variable, * or replace or delete an existing one. |
2598090b7
|
215 |
*/ |
94b467b14
|
216 |
static int _do_env_set(int flag, int argc, char * const argv[], int env_flag) |
c3f652585
|
217 218 219 220 |
{ int i, len; char *name, *value, *s; ENTRY e, *ep; |
24ab5a191
|
221 222 |
debug("Initial value for argc=%d ", argc); |
49d81fdfb
|
223 224 225 226 227 |
#if CONFIG_IS_ENABLED(CMD_NVEDIT_EFI) if (argc > 1 && argv[1][0] == '-' && argv[1][1] == 'e') return do_env_set_efi(NULL, flag, --argc, ++argv); #endif |
24ab5a191
|
228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 |
while (argc > 1 && **(argv + 1) == '-') { char *arg = *++argv; --argc; while (*++arg) { switch (*arg) { case 'f': /* force */ env_flag |= H_FORCE; break; default: return CMD_RET_USAGE; } } } debug("Final value for argc=%d ", argc); |
c3f652585
|
244 |
name = argv[1]; |
c3f652585
|
245 246 247 248 249 250 251 252 253 |
if (strchr(name, '=')) { printf("## Error: illegal character '='" "in variable name \"%s\" ", name); return 1; } env_id++; |
c3f652585
|
254 |
|
a68d3ed0a
|
255 |
/* Delete only ? */ |
d09b1787a
|
256 |
if (argc < 3 || argv[2] == NULL) { |
24ab5a191
|
257 |
int rc = hdelete_r(name, &env_htab, env_flag); |
ea882baf9
|
258 |
return !rc; |
a68d3ed0a
|
259 260 261 |
} /* |
ea882baf9
|
262 |
* Insert / replace new value |
a68d3ed0a
|
263 |
*/ |
f3c615b8a
|
264 |
for (i = 2, len = 0; i < argc; ++i) |
a68d3ed0a
|
265 |
len += strlen(argv[i]) + 1; |
f3c615b8a
|
266 267 268 |
value = malloc(len); if (value == NULL) { |
ea882baf9
|
269 270 |
printf("## Can't malloc %d bytes ", len); |
a68d3ed0a
|
271 272 |
return 1; } |
f3c615b8a
|
273 |
for (i = 2, s = value; i < argc; ++i) { |
ea882baf9
|
274 |
char *v = argv[i]; |
a68d3ed0a
|
275 |
|
ea882baf9
|
276 |
while ((*s++ = *v++) != '\0') |
a68d3ed0a
|
277 |
; |
d09b1787a
|
278 |
*(s - 1) = ' '; |
ea882baf9
|
279 280 281 |
} if (s != value) *--s = '\0'; |
d09b1787a
|
282 283 |
e.key = name; e.data = value; |
24ab5a191
|
284 |
hsearch_r(e, ENTER, &ep, &env_htab, env_flag); |
ea882baf9
|
285 286 287 288 289 290 |
free(value); if (!ep) { printf("## Error inserting \"%s\" variable, errno=%d ", name, errno); return 1; |
a68d3ed0a
|
291 |
} |
a68d3ed0a
|
292 |
|
a68d3ed0a
|
293 294 |
return 0; } |
382bee57f
|
295 |
int env_set(const char *varname, const char *varvalue) |
a68d3ed0a
|
296 |
{ |
84b5e8022
|
297 |
const char * const argv[4] = { "setenv", varname, varvalue, NULL }; |
a7eb1d66c
|
298 299 300 |
/* before import into hashtable */ if (!(gd->flags & GD_FLG_ENV_READY)) return 1; |
d09b1787a
|
301 |
if (varvalue == NULL || varvalue[0] == '\0') |
94b467b14
|
302 |
return _do_env_set(0, 2, (char * const *)argv, H_PROGRAMMATIC); |
9ffd451af
|
303 |
else |
94b467b14
|
304 |
return _do_env_set(0, 3, (char * const *)argv, H_PROGRAMMATIC); |
a68d3ed0a
|
305 |
} |
d67f10ce0
|
306 307 308 |
/** * Set an environment variable to an integer value * |
9602286d3
|
309 |
* @param varname Environment variable to set |
d67f10ce0
|
310 311 312 |
* @param value Value to set it to * @return 0 if ok, 1 on error */ |
018f53032
|
313 |
int env_set_ulong(const char *varname, ulong value) |
d67f10ce0
|
314 315 316 |
{ /* TODO: this should be unsigned */ char *str = simple_itoa(value); |
382bee57f
|
317 |
return env_set(varname, str); |
d67f10ce0
|
318 319 320 |
} /** |
bfc599664
|
321 |
* Set an environment variable to an value in hex |
d67f10ce0
|
322 |
* |
9602286d3
|
323 |
* @param varname Environment variable to set |
bfc599664
|
324 |
* @param value Value to set it to |
d67f10ce0
|
325 326 |
* @return 0 if ok, 1 on error */ |
018f53032
|
327 |
int env_set_hex(const char *varname, ulong value) |
d67f10ce0
|
328 329 |
{ char str[17]; |
bfc599664
|
330 |
sprintf(str, "%lx", value); |
382bee57f
|
331 |
return env_set(varname, str); |
d67f10ce0
|
332 |
} |
bfebc8c96
|
333 |
ulong env_get_hex(const char *varname, ulong default_val) |
76b8f79c2
|
334 335 336 337 |
{ const char *s; ulong value; char *endp; |
00caae6d4
|
338 |
s = env_get(varname); |
76b8f79c2
|
339 340 341 342 343 344 345 |
if (s) value = simple_strtoul(s, &endp, 16); if (!s || endp == s) return default_val; return value; } |
9925f1dbc
|
346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370 371 372 373 374 |
void eth_parse_enetaddr(const char *addr, uint8_t *enetaddr) { char *end; int i; for (i = 0; i < 6; ++i) { enetaddr[i] = addr ? simple_strtoul(addr, &end, 16) : 0; if (addr) addr = (*end) ? end + 1 : end; } } int eth_env_get_enetaddr(const char *name, uint8_t *enetaddr) { eth_parse_enetaddr(env_get(name), enetaddr); return is_valid_ethaddr(enetaddr); } int eth_env_set_enetaddr(const char *name, const uint8_t *enetaddr) { char buf[ARP_HLEN_ASCII + 1]; if (eth_env_get_enetaddr(name, (uint8_t *)buf)) return -EEXIST; sprintf(buf, "%pM", enetaddr); return env_set(name, buf); } |
7ac2fe2da
|
375 |
#ifndef CONFIG_SPL_BUILD |
088f1b199
|
376 |
static int do_env_set(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
a68d3ed0a
|
377 |
{ |
47e26b1bf
|
378 |
if (argc < 2) |
4c12eeb8b
|
379 |
return CMD_RET_USAGE; |
a68d3ed0a
|
380 |
|
94b467b14
|
381 |
return _do_env_set(flag, argc, argv, H_INTERACTIVE); |
a68d3ed0a
|
382 |
} |
ea882baf9
|
383 |
/* |
a68d3ed0a
|
384 385 |
* Prompt for environment variable */ |
c76fe4742
|
386 |
#if defined(CONFIG_CMD_ASKENV) |
f3c615b8a
|
387 |
int do_env_ask(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
a68d3ed0a
|
388 |
{ |
6d0f6bcf3
|
389 |
char message[CONFIG_SYS_CBSIZE]; |
7d85591dd
|
390 |
int i, len, pos, size; |
a68d3ed0a
|
391 |
char *local_args[4]; |
7d85591dd
|
392 |
char *endptr; |
a68d3ed0a
|
393 394 395 396 397 |
local_args[0] = argv[0]; local_args[1] = argv[1]; local_args[2] = NULL; local_args[3] = NULL; |
7d85591dd
|
398 399 400 401 402 403 |
/* * Check the syntax: * * env_ask envname [message1 ...] [size] */ if (argc == 1) |
4c12eeb8b
|
404 |
return CMD_RET_USAGE; |
a68d3ed0a
|
405 |
|
7d85591dd
|
406 407 408 409 410 411 412 413 414 415 416 417 418 |
/* * We test the last argument if it can be converted * into a decimal number. If yes, we assume it's * the size. Otherwise we echo it as part of the * message. */ i = simple_strtoul(argv[argc - 1], &endptr, 10); if (*endptr != '\0') { /* no size */ size = CONFIG_SYS_CBSIZE - 1; } else { /* size given */ size = i; --argc; } |
a68d3ed0a
|
419 |
|
7d85591dd
|
420 421 422 423 |
if (argc <= 2) { sprintf(message, "Please enter '%s': ", argv[1]); } else { /* env_ask envname message1 ... messagen [size] */ |
bf52fcdef
|
424 |
for (i = 2, pos = 0; i < argc && pos+1 < sizeof(message); i++) { |
f3c615b8a
|
425 |
if (pos) |
a68d3ed0a
|
426 |
message[pos++] = ' '; |
f3c615b8a
|
427 |
|
c667723ff
|
428 |
strncpy(message + pos, argv[i], sizeof(message) - pos); |
a68d3ed0a
|
429 430 |
pos += strlen(argv[i]); } |
c667723ff
|
431 432 433 434 435 |
if (pos < sizeof(message) - 1) { message[pos++] = ' '; message[pos] = '\0'; } else message[CONFIG_SYS_CBSIZE - 1] = '\0'; |
a68d3ed0a
|
436 |
} |
6d0f6bcf3
|
437 438 |
if (size >= CONFIG_SYS_CBSIZE) size = CONFIG_SYS_CBSIZE - 1; |
a68d3ed0a
|
439 440 441 442 443 |
if (size <= 0) return 1; /* prompt for input */ |
e1bf824df
|
444 |
len = cli_readline(message); |
a68d3ed0a
|
445 446 447 448 449 450 451 452 453 454 455 |
if (size < len) console_buffer[size] = '\0'; len = 2; if (console_buffer[0] != '\0') { local_args[2] = console_buffer; len = 3; } /* Continue calling setenv code */ |
94b467b14
|
456 |
return _do_env_set(flag, len, local_args, H_INTERACTIVE); |
a68d3ed0a
|
457 |
} |
902531788
|
458 |
#endif |
a68d3ed0a
|
459 |
|
5e2b3e0c5
|
460 |
#if defined(CONFIG_CMD_ENV_CALLBACK) |
cca98fd6a
|
461 462 |
static int print_static_binding(const char *var_name, const char *callback_name, void *priv) |
5e2b3e0c5
|
463 464 465 466 467 468 469 470 471 472 473 474 475 476 477 478 479 480 481 482 483 484 485 486 487 488 489 490 491 492 493 494 495 496 497 498 499 500 501 502 503 504 505 506 507 508 509 510 511 512 513 514 515 516 517 518 519 520 521 522 523 524 525 526 527 528 529 530 531 532 533 534 |
{ printf("\t%-20s %-20s ", var_name, callback_name); return 0; } static int print_active_callback(ENTRY *entry) { struct env_clbk_tbl *clbkp; int i; int num_callbacks; if (entry->callback == NULL) return 0; /* look up the callback in the linker-list */ num_callbacks = ll_entry_count(struct env_clbk_tbl, env_clbk); for (i = 0, clbkp = ll_entry_start(struct env_clbk_tbl, env_clbk); i < num_callbacks; i++, clbkp++) { #if defined(CONFIG_NEEDS_MANUAL_RELOC) if (entry->callback == clbkp->callback + gd->reloc_off) #else if (entry->callback == clbkp->callback) #endif break; } if (i == num_callbacks) /* this should probably never happen, but just in case... */ printf("\t%-20s %p ", entry->key, entry->callback); else printf("\t%-20s %-20s ", entry->key, clbkp->name); return 0; } /* * Print the callbacks available and what they are bound to */ int do_env_callback(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) { struct env_clbk_tbl *clbkp; int i; int num_callbacks; /* Print the available callbacks */ puts("Available callbacks: "); puts("\tCallback Name "); puts("\t------------- "); num_callbacks = ll_entry_count(struct env_clbk_tbl, env_clbk); for (i = 0, clbkp = ll_entry_start(struct env_clbk_tbl, env_clbk); i < num_callbacks; i++, clbkp++) printf("\t%s ", clbkp->name); puts(" "); /* Print the static bindings that may exist */ puts("Static callback bindings: "); printf("\t%-20s %-20s ", "Variable Name", "Callback Name"); printf("\t%-20s %-20s ", "-------------", "-------------"); |
cca98fd6a
|
535 |
env_attr_walk(ENV_CALLBACK_LIST_STATIC, print_static_binding, NULL); |
5e2b3e0c5
|
536 537 538 539 540 541 542 543 544 545 546 547 548 549 |
puts(" "); /* walk through each variable and print the callback if it has one */ puts("Active callback bindings: "); printf("\t%-20s %-20s ", "Variable Name", "Callback Name"); printf("\t%-20s %-20s ", "-------------", "-------------"); hwalk_r(&env_htab, print_active_callback); return 0; } #endif |
fffad71bc
|
550 |
#if defined(CONFIG_CMD_ENV_FLAGS) |
cca98fd6a
|
551 552 |
static int print_static_flags(const char *var_name, const char *flags, void *priv) |
fffad71bc
|
553 554 |
{ enum env_flags_vartype type = env_flags_parse_vartype(flags); |
267541f77
|
555 |
enum env_flags_varaccess access = env_flags_parse_varaccess(flags); |
fffad71bc
|
556 |
|
267541f77
|
557 558 559 560 |
printf("\t%-20s %-20s %-20s ", var_name, env_flags_get_vartype_name(type), env_flags_get_varaccess_name(access)); |
fffad71bc
|
561 562 563 564 565 566 567 |
return 0; } static int print_active_flags(ENTRY *entry) { enum env_flags_vartype type; |
267541f77
|
568 |
enum env_flags_varaccess access; |
fffad71bc
|
569 570 571 572 573 574 |
if (entry->flags == 0) return 0; type = (enum env_flags_vartype) (entry->flags & ENV_FLAGS_VARTYPE_BIN_MASK); |
267541f77
|
575 576 577 578 579 |
access = env_flags_parse_varaccess_from_binflags(entry->flags); printf("\t%-20s %-20s %-20s ", entry->key, env_flags_get_vartype_name(type), env_flags_get_varaccess_name(access)); |
fffad71bc
|
580 581 582 583 584 585 586 587 588 589 590 591 592 593 594 595 596 597 598 599 |
return 0; } /* * Print the flags available and what variables have flags */ int do_env_flags(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) { /* Print the available variable types */ printf("Available variable type flags (position %d): ", ENV_FLAGS_VARTYPE_LOC); puts("\tFlag\tVariable Type Name "); puts("\t----\t------------------ "); env_flags_print_vartypes(); puts(" "); |
267541f77
|
600 601 602 603 604 605 606 607 608 609 610 |
/* Print the available variable access types */ printf("Available variable access flags (position %d): ", ENV_FLAGS_VARACCESS_LOC); puts("\tFlag\tVariable Access Name "); puts("\t----\t-------------------- "); env_flags_print_varaccess(); puts(" "); |
fffad71bc
|
611 612 613 |
/* Print the static flags that may exist */ puts("Static flags: "); |
267541f77
|
614 615 616 617 618 619 |
printf("\t%-20s %-20s %-20s ", "Variable Name", "Variable Type", "Variable Access"); printf("\t%-20s %-20s %-20s ", "-------------", "-------------", "---------------"); |
cca98fd6a
|
620 |
env_attr_walk(ENV_FLAGS_LIST_STATIC, print_static_flags, NULL); |
fffad71bc
|
621 622 623 624 625 626 |
puts(" "); /* walk through each variable and print the flags if non-default */ puts("Active flags: "); |
267541f77
|
627 628 629 630 631 632 |
printf("\t%-20s %-20s %-20s ", "Variable Name", "Variable Type", "Variable Access"); printf("\t%-20s %-20s %-20s ", "-------------", "-------------", "---------------"); |
fffad71bc
|
633 634 635 636 |
hwalk_r(&env_htab, print_active_flags); return 0; } #endif |
ea882baf9
|
637 |
/* |
246c69225
|
638 639 640 |
* Interactively edit an environment variable */ #if defined(CONFIG_CMD_EDITENV) |
088f1b199
|
641 642 |
static int do_env_edit(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
246c69225
|
643 644 645 |
{ char buffer[CONFIG_SYS_CBSIZE]; char *init_val; |
246c69225
|
646 |
|
47e26b1bf
|
647 |
if (argc < 2) |
4c12eeb8b
|
648 |
return CMD_RET_USAGE; |
246c69225
|
649 |
|
94b467b14
|
650 651 652 |
/* before import into hashtable */ if (!(gd->flags & GD_FLG_ENV_READY)) return 1; |
246c69225
|
653 |
/* Set read buffer to initial value or empty sting */ |
00caae6d4
|
654 |
init_val = env_get(argv[1]); |
246c69225
|
655 |
if (init_val) |
5d49b4cdf
|
656 |
snprintf(buffer, CONFIG_SYS_CBSIZE, "%s", init_val); |
246c69225
|
657 658 |
else buffer[0] = '\0'; |
e1bf824df
|
659 |
if (cli_readline_into_buffer("edit: ", buffer, 0) < 0) |
18a3cce9f
|
660 |
return 1; |
246c69225
|
661 |
|
94b467b14
|
662 663 664 665 666 667 668 669 670 671 |
if (buffer[0] == '\0') { const char * const _argv[3] = { "setenv", argv[1], NULL }; return _do_env_set(0, 2, (char * const *)_argv, H_INTERACTIVE); } else { const char * const _argv[4] = { "setenv", argv[1], buffer, NULL }; return _do_env_set(0, 3, (char * const *)_argv, H_INTERACTIVE); } |
246c69225
|
672 673 |
} #endif /* CONFIG_CMD_EDITENV */ |
7ac2fe2da
|
674 |
#endif /* CONFIG_SPL_BUILD */ |
246c69225
|
675 |
|
ea882baf9
|
676 |
/* |
a68d3ed0a
|
677 678 679 680 |
* Look up variable from environment, * return address of storage for that variable, * or NULL if not found */ |
00caae6d4
|
681 |
char *env_get(const char *name) |
a68d3ed0a
|
682 |
{ |
d09b1787a
|
683 |
if (gd->flags & GD_FLG_ENV_READY) { /* after import into hashtable */ |
ea882baf9
|
684 |
ENTRY e, *ep; |
a68d3ed0a
|
685 |
|
91a76751a
|
686 |
WATCHDOG_RESET(); |
2a3cb0207
|
687 |
|
d09b1787a
|
688 689 |
e.key = name; e.data = NULL; |
c4e0057fa
|
690 |
hsearch_r(e, FIND, &ep, &env_htab, 0); |
91a76751a
|
691 |
|
f3c615b8a
|
692 |
return ep ? ep->data : NULL; |
a68d3ed0a
|
693 |
} |
ea882baf9
|
694 |
/* restricted capabilities before import */ |
00caae6d4
|
695 |
if (env_get_f(name, (char *)(gd->env_buf), sizeof(gd->env_buf)) > 0) |
ea882baf9
|
696 |
return (char *)(gd->env_buf); |
91a76751a
|
697 |
|
ea882baf9
|
698 |
return NULL; |
a68d3ed0a
|
699 |
} |
ea882baf9
|
700 701 702 |
/* * Look up variable from environment for restricted C runtime env. */ |
00caae6d4
|
703 |
int env_get_f(const char *name, char *buf, unsigned len) |
a68d3ed0a
|
704 |
{ |
87c7fb396
|
705 |
int i, nxt, c; |
a68d3ed0a
|
706 |
|
d09b1787a
|
707 |
for (i = 0; env_get_char(i) != '\0'; i = nxt + 1) { |
a68d3ed0a
|
708 |
int val, n; |
87c7fb396
|
709 710 711 |
for (nxt = i; (c = env_get_char(nxt)) != '\0'; ++nxt) { if (c < 0) return c; |
f3c615b8a
|
712 713 |
if (nxt >= CONFIG_ENV_SIZE) return -1; |
a68d3ed0a
|
714 |
} |
f3c615b8a
|
715 716 717 |
val = envmatch((uchar *)name, i); if (val < 0) |
a68d3ed0a
|
718 |
continue; |
9ed4a9582
|
719 |
|
a68d3ed0a
|
720 |
/* found; copy out */ |
f3c615b8a
|
721 |
for (n = 0; n < len; ++n, ++buf) { |
87c7fb396
|
722 723 724 725 |
c = env_get_char(val++); if (c < 0) return c; *buf = c; |
d09b1787a
|
726 |
if (*buf == '\0') |
9ed4a9582
|
727 728 729 730 731 |
return n; } if (n) *--buf = '\0'; |
82919517f
|
732 733 734 |
printf("env_buf [%u bytes] too small for value of \"%s\" ", len, name); |
9ed4a9582
|
735 736 |
return n; |
a68d3ed0a
|
737 |
} |
d09b1787a
|
738 |
|
f3c615b8a
|
739 |
return -1; |
a68d3ed0a
|
740 |
} |
4a9b41310
|
741 742 743 |
/** * Decode the integer value of an environment variable and return it. * |
919d25c92
|
744 |
* @param name Name of environment variable |
4a9b41310
|
745 746 747 748 749 |
* @param base Number base to use (normally 10, or 16 for hex) * @param default_val Default value to return if the variable is not * found * @return the decoded value, or default_val if not found */ |
bfebc8c96
|
750 |
ulong env_get_ulong(const char *name, int base, ulong default_val) |
4a9b41310
|
751 752 |
{ /* |
00caae6d4
|
753 |
* We can use env_get() here, even before relocation, since the |
4a9b41310
|
754 755 |
* environment variable value is an integer and thus short. */ |
00caae6d4
|
756 |
const char *str = env_get(name); |
4a9b41310
|
757 758 759 |
return str ? simple_strtoul(str, NULL, base) : default_val; } |
7ac2fe2da
|
760 |
#ifndef CONFIG_SPL_BUILD |
bdab39d35
|
761 |
#if defined(CONFIG_CMD_SAVEENV) && !defined(CONFIG_ENV_IS_NOWHERE) |
088f1b199
|
762 763 |
static int do_env_save(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
a68d3ed0a
|
764 |
{ |
01510091d
|
765 |
return env_save() ? 1 : 0; |
a68d3ed0a
|
766 |
} |
8bde7f776
|
767 |
|
ba69dc26a
|
768 |
U_BOOT_CMD( |
ea882baf9
|
769 |
saveenv, 1, 0, do_env_save, |
2fb2604d5
|
770 |
"save environment variables to persistent storage", |
a89c33db9
|
771 |
"" |
ba69dc26a
|
772 |
); |
a68d3ed0a
|
773 |
#endif |
7ac2fe2da
|
774 |
#endif /* CONFIG_SPL_BUILD */ |
a68d3ed0a
|
775 |
|
ea882baf9
|
776 |
/* |
a68d3ed0a
|
777 778 779 780 |
* Match a name / name=value pair * * s1 is either a simple 'name', or a 'name=value' pair. * i2 is the environment index for a 'name2=value2' pair. |
d09b1787a
|
781 |
* If the names match, return the index for the value2, else -1. |
a68d3ed0a
|
782 |
*/ |
f3c615b8a
|
783 |
int envmatch(uchar *s1, int i2) |
a68d3ed0a
|
784 |
{ |
586197dfe
|
785 786 |
if (s1 == NULL) return -1; |
a68d3ed0a
|
787 788 |
while (*s1 == env_get_char(i2++)) if (*s1++ == '=') |
f3c615b8a
|
789 |
return i2; |
d09b1787a
|
790 |
|
a68d3ed0a
|
791 |
if (*s1 == '\0' && env_get_char(i2-1) == '=') |
f3c615b8a
|
792 |
return i2; |
d09b1787a
|
793 |
|
f3c615b8a
|
794 |
return -1; |
a68d3ed0a
|
795 |
} |
8bde7f776
|
796 |
|
7ac2fe2da
|
797 |
#ifndef CONFIG_SPL_BUILD |
30091494e
|
798 |
static int do_env_default(cmd_tbl_t *cmdtp, int flag, |
d09b1787a
|
799 |
int argc, char * const argv[]) |
ea882baf9
|
800 |
{ |
5a04264ec
|
801 |
int all = 0, env_flag = H_INTERACTIVE; |
f3c615b8a
|
802 |
|
b64b7c3df
|
803 804 805 806 807 808 809 810 811 812 813 |
debug("Initial value for argc=%d ", argc); while (--argc > 0 && **++argv == '-') { char *arg = *argv; while (*++arg) { switch (*arg) { case 'a': /* default all */ all = 1; break; case 'f': /* force */ |
30091494e
|
814 |
env_flag |= H_FORCE; |
b64b7c3df
|
815 816 817 818 819 820 821 822 823 824 |
break; default: return cmd_usage(cmdtp); } } } debug("Final value for argc=%d ", argc); if (all && (argc == 0)) { /* Reset the whole environment */ |
c5d548a9f
|
825 826 827 |
set_default_env("## Resetting to default environment ", env_flag); |
b64b7c3df
|
828 829 830 831 |
return 0; } if (!all && (argc > 0)) { /* Reset individual variables */ |
477f8116d
|
832 |
set_default_vars(argc, argv, env_flag); |
b64b7c3df
|
833 834 835 836 |
return 0; } return cmd_usage(cmdtp); |
ea882baf9
|
837 |
} |
d09b1787a
|
838 839 |
static int do_env_delete(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
ea882baf9
|
840 |
{ |
9d8d661d7
|
841 842 843 844 845 846 847 848 849 850 851 852 853 854 855 856 857 858 859 860 861 862 863 864 865 866 867 868 869 870 871 872 |
int env_flag = H_INTERACTIVE; int ret = 0; debug("Initial value for argc=%d ", argc); while (argc > 1 && **(argv + 1) == '-') { char *arg = *++argv; --argc; while (*++arg) { switch (*arg) { case 'f': /* force */ env_flag |= H_FORCE; break; default: return CMD_RET_USAGE; } } } debug("Final value for argc=%d ", argc); env_id++; while (--argc > 0) { char *name = *++argv; if (!hdelete_r(name, &env_htab, env_flag)) ret = 1; } return ret; |
ea882baf9
|
873 |
} |
0c79cda01
|
874 |
#ifdef CONFIG_CMD_EXPORTENV |
ea882baf9
|
875 |
/* |
37f2fe747
|
876 |
* env export [-t | -b | -c] [-s size] addr [var ...] |
ea882baf9
|
877 878 879 880 881 882 883 884 885 |
* -t: export as text format; if size is given, data will be * padded with '\0' bytes; if not, one terminating '\0' * will be added (which is included in the "filesize" * setting so you can for exmple copy this to flash and * keep the termination). * -b: export as binary format (name=value pairs separated by * '\0', list end marked by double "\0\0") * -c: export as checksum protected environment format as * used for example by "saveenv" command |
37f2fe747
|
886 887 |
* -s size: * size of output buffer |
ea882baf9
|
888 |
* addr: memory address where environment gets stored |
37f2fe747
|
889 890 891 |
* var... List of variable names that get included into the * export. Without arguments, the whole environment gets * exported. |
ea882baf9
|
892 893 894 895 |
* * With "-c" and size is NOT given, then the export command will * format the data as currently used for the persistent storage, * i. e. it will use CONFIG_ENV_SECT_SIZE as output block size and |
fc0b5948e
|
896 |
* prepend a valid CRC32 checksum and, in case of redundant |
ea882baf9
|
897 898 899 900 901 902 903 904 |
* environment, a "current" redundancy flag. If size is given, this * value will be used instead of CONFIG_ENV_SECT_SIZE; again, CRC32 * checksum and redundancy flag will be inserted. * * With "-b" and "-t", always only the real data (including a * terminating '\0' byte) will be written; here the optional size * argument will be used to make sure not to overflow the user * provided buffer; the command will abort if the size is not |
fc0b5948e
|
905 |
* sufficient. Any remaining space will be '\0' padded. |
ea882baf9
|
906 907 908 909 |
* * On successful return, the variable "filesize" will be set. * Note that filesize includes the trailing/terminating '\0' byte(s). * |
fc0b5948e
|
910 |
* Usage scenario: create a text snapshot/backup of the current settings: |
ea882baf9
|
911 912 913 914 915 916 917 918 919 |
* * => env export -t 100000 * => era ${backup_addr} +${filesize} * => cp.b 100000 ${backup_addr} ${filesize} * * Re-import this snapshot, deleting all other settings: * * => env import -d -t ${backup_addr} */ |
d09b1787a
|
920 921 |
static int do_env_export(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
ea882baf9
|
922 923 |
{ char buf[32]; |
fd37dac9e
|
924 925 |
ulong addr; char *ptr, *cmd, *res; |
37f2fe747
|
926 |
size_t size = 0; |
ea882baf9
|
927 928 929 930 931 932 933 934 935 936 937 938 939 940 941 942 943 944 945 946 947 948 949 950 |
ssize_t len; env_t *envp; char sep = ' '; int chk = 0; int fmt = 0; cmd = *argv; while (--argc > 0 && **++argv == '-') { char *arg = *argv; while (*++arg) { switch (*arg) { case 'b': /* raw binary format */ if (fmt++) goto sep_err; sep = '\0'; break; case 'c': /* external checksum format */ if (fmt++) goto sep_err; sep = '\0'; chk = 1; break; |
37f2fe747
|
951 952 953 954 955 |
case 's': /* size given */ if (--argc <= 0) return cmd_usage(cmdtp); size = simple_strtoul(*++argv, NULL, 16); goto NXTARG; |
ea882baf9
|
956 957 958 959 960 961 962 |
case 't': /* text format */ if (fmt++) goto sep_err; sep = ' '; break; default: |
4c12eeb8b
|
963 |
return CMD_RET_USAGE; |
ea882baf9
|
964 965 |
} } |
37f2fe747
|
966 |
NXTARG: ; |
ea882baf9
|
967 |
} |
f3c615b8a
|
968 |
if (argc < 1) |
4c12eeb8b
|
969 |
return CMD_RET_USAGE; |
8bde7f776
|
970 |
|
fd37dac9e
|
971 972 |
addr = simple_strtoul(argv[0], NULL, 16); ptr = map_sysmem(addr, size); |
ea882baf9
|
973 |
|
37f2fe747
|
974 |
if (size) |
fd37dac9e
|
975 |
memset(ptr, '\0', size); |
37f2fe747
|
976 977 978 |
argc--; argv++; |
ea882baf9
|
979 980 |
if (sep) { /* export as text file */ |
ea009d474
|
981 982 |
len = hexport_r(&env_htab, sep, H_MATCH_KEY | H_MATCH_IDENT, |
fd37dac9e
|
983 |
&ptr, size, argc, argv); |
ea882baf9
|
984 |
if (len < 0) { |
6c90f6233
|
985 986 987 |
pr_err("## Error: Cannot export environment: errno = %d ", errno); |
ea882baf9
|
988 989 |
return 1; } |
8c3aff525
|
990 |
sprintf(buf, "%zX", (size_t)len); |
382bee57f
|
991 |
env_set("filesize", buf); |
ea882baf9
|
992 993 994 |
return 0; } |
fd37dac9e
|
995 |
envp = (env_t *)ptr; |
ea882baf9
|
996 997 998 999 |
if (chk) /* export as checksum protected block */ res = (char *)envp->data; else /* export as raw binary data */ |
fd37dac9e
|
1000 |
res = ptr; |
ea882baf9
|
1001 |
|
ea009d474
|
1002 1003 1004 |
len = hexport_r(&env_htab, '\0', H_MATCH_KEY | H_MATCH_IDENT, &res, ENV_SIZE, argc, argv); |
ea882baf9
|
1005 |
if (len < 0) { |
6c90f6233
|
1006 1007 1008 |
pr_err("## Error: Cannot export environment: errno = %d ", errno); |
ea882baf9
|
1009 1010 1011 1012 |
return 1; } if (chk) { |
d71b029d1
|
1013 1014 |
envp->crc = crc32(0, envp->data, size ? size - offsetof(env_t, data) : ENV_SIZE); |
ea882baf9
|
1015 1016 1017 1018 |
#ifdef CONFIG_ENV_ADDR_REDUND envp->flags = ACTIVE_FLAG; #endif } |
018f53032
|
1019 |
env_set_hex("filesize", len + offsetof(env_t, data)); |
ea882baf9
|
1020 1021 1022 1023 |
return 0; sep_err: |
6c90f6233
|
1024 1025 1026 |
printf("## Error: %s: only one of \"-b\", \"-c\" or \"-t\" allowed ", cmd); |
ea882baf9
|
1027 1028 |
return 1; } |
0c79cda01
|
1029 |
#endif |
ea882baf9
|
1030 |
|
0c79cda01
|
1031 |
#ifdef CONFIG_CMD_IMPORTENV |
ea882baf9
|
1032 |
/* |
eaf734724
|
1033 1034 1035 1036 1037 |
* env import [-d] [-t [-r] | -b | -c] addr [size] [var ...] * -d: delete existing environment before importing if no var is * passed; if vars are passed, if one var is in the current * environment but not in the environment at addr, delete var from * current environment; |
fc0b5948e
|
1038 |
* otherwise overwrite / append to existing definitions |
ea882baf9
|
1039 1040 |
* -t: assume text format; either "size" must be given or the * text data must be '\0' terminated |
ecd1446fe
|
1041 1042 1043 1044 |
* -r: handle CRLF like LF, that means exported variables with * a content which ends with \r won't get imported. Used * to import text files created with editors which are using CRLF * for line endings. Only effective in addition to -t. |
ea882baf9
|
1045 1046 1047 1048 1049 |
* -b: assume binary format ('\0' separated, "\0\0" terminated) * -c: assume checksum protected environment format * addr: memory address to read from * size: length of input data; if missing, proper '\0' * termination is mandatory |
eaf734724
|
1050 1051 1052 1053 1054 |
* if var is set and size should be missing (i.e. '\0' * termination), set size to '-' * var... List of the names of the only variables that get imported from * the environment at address 'addr'. Without arguments, the whole * environment gets imported. |
ea882baf9
|
1055 |
*/ |
d09b1787a
|
1056 1057 |
static int do_env_import(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
ea882baf9
|
1058 |
{ |
fd37dac9e
|
1059 1060 |
ulong addr; char *cmd, *ptr; |
ea882baf9
|
1061 1062 1063 1064 1065 |
char sep = ' '; int chk = 0; int fmt = 0; int del = 0; |
ecd1446fe
|
1066 |
int crlf_is_lf = 0; |
eaf734724
|
1067 |
int wl = 0; |
ea882baf9
|
1068 1069 1070 1071 1072 1073 1074 1075 1076 1077 1078 1079 1080 1081 1082 1083 1084 1085 1086 1087 1088 1089 1090 1091 1092 |
size_t size; cmd = *argv; while (--argc > 0 && **++argv == '-') { char *arg = *argv; while (*++arg) { switch (*arg) { case 'b': /* raw binary format */ if (fmt++) goto sep_err; sep = '\0'; break; case 'c': /* external checksum format */ if (fmt++) goto sep_err; sep = '\0'; chk = 1; break; case 't': /* text format */ if (fmt++) goto sep_err; sep = ' '; break; |
ecd1446fe
|
1093 1094 1095 |
case 'r': /* handle CRLF like LF */ crlf_is_lf = 1; break; |
ea882baf9
|
1096 1097 1098 1099 |
case 'd': del = 1; break; default: |
4c12eeb8b
|
1100 |
return CMD_RET_USAGE; |
ea882baf9
|
1101 1102 1103 |
} } } |
f3c615b8a
|
1104 |
if (argc < 1) |
4c12eeb8b
|
1105 |
return CMD_RET_USAGE; |
ea882baf9
|
1106 1107 1108 1109 |
if (!fmt) printf("## Warning: defaulting to text format "); |
ecd1446fe
|
1110 1111 1112 |
if (sep != ' ' && crlf_is_lf ) crlf_is_lf = 0; |
fd37dac9e
|
1113 1114 |
addr = simple_strtoul(argv[0], NULL, 16); ptr = map_sysmem(addr, 0); |
ea882baf9
|
1115 |
|
eaf734724
|
1116 |
if (argc >= 2 && strcmp(argv[1], "-")) { |
ea882baf9
|
1117 |
size = simple_strtoul(argv[1], NULL, 16); |
eaf734724
|
1118 |
} else if (chk) { |
3775dcd9c
|
1119 1120 1121 |
puts("## Error: external checksum format must pass size "); return CMD_RET_FAILURE; |
ea882baf9
|
1122 |
} else { |
fd37dac9e
|
1123 |
char *s = ptr; |
ea882baf9
|
1124 1125 1126 1127 1128 1129 1130 1131 1132 1133 1134 1135 1136 1137 |
size = 0; while (size < MAX_ENV_SIZE) { if ((*s == sep) && (*(s+1) == '\0')) break; ++s; ++size; } if (size == MAX_ENV_SIZE) { printf("## Warning: Input data exceeds %d bytes" " - truncated ", MAX_ENV_SIZE); } |
d3f80c77c
|
1138 |
size += 2; |
79afc88d2
|
1139 1140 |
printf("## Info: input data size = %zu = 0x%zX ", size, size); |
ea882baf9
|
1141 |
} |
eaf734724
|
1142 1143 |
if (argc > 2) wl = 1; |
ea882baf9
|
1144 1145 |
if (chk) { uint32_t crc; |
fd37dac9e
|
1146 |
env_t *ep = (env_t *)ptr; |
ea882baf9
|
1147 1148 1149 1150 1151 1152 1153 1154 1155 |
size -= offsetof(env_t, data); memcpy(&crc, &ep->crc, sizeof(crc)); if (crc32(0, ep->data, size) != crc) { puts("## Error: bad CRC, import failed "); return 1; } |
fd37dac9e
|
1156 |
ptr = (char *)ep->data; |
ea882baf9
|
1157 |
} |
eaf734724
|
1158 1159 |
if (!himport_r(&env_htab, ptr, size, sep, del ? 0 : H_NOCLEAR, crlf_is_lf, wl ? argc - 2 : 0, wl ? &argv[2] : NULL)) { |
6c90f6233
|
1160 1161 1162 |
pr_err("## Error: Environment import failed: errno = %d ", errno); |
ea882baf9
|
1163 1164 1165 1166 1167 1168 1169 1170 1171 1172 1173 1174 |
return 1; } gd->flags |= GD_FLG_ENV_READY; return 0; sep_err: printf("## %s: only one of \"-b\", \"-c\" or \"-t\" allowed ", cmd); return 1; } |
0c79cda01
|
1175 |
#endif |
ea882baf9
|
1176 |
|
88733e2c6
|
1177 1178 1179 1180 1181 1182 1183 1184 1185 1186 1187 1188 1189 1190 1191 1192 |
#if defined(CONFIG_CMD_ENV_EXISTS) static int do_env_exists(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) { ENTRY e, *ep; if (argc < 2) return CMD_RET_USAGE; e.key = argv[1]; e.data = NULL; hsearch_r(e, FIND, &ep, &env_htab, 0); return (ep == NULL) ? 1 : 0; } #endif |
ea882baf9
|
1193 1194 1195 1196 1197 1198 1199 1200 |
/* * New command line interface: "env" command with subcommands */ static cmd_tbl_t cmd_env_sub[] = { #if defined(CONFIG_CMD_ASKENV) U_BOOT_CMD_MKENT(ask, CONFIG_SYS_MAXARGS, 1, do_env_ask, "", ""), #endif U_BOOT_CMD_MKENT(default, 1, 0, do_env_default, "", ""), |
9d8d661d7
|
1201 |
U_BOOT_CMD_MKENT(delete, CONFIG_SYS_MAXARGS, 0, do_env_delete, "", ""), |
ea882baf9
|
1202 1203 1204 |
#if defined(CONFIG_CMD_EDITENV) U_BOOT_CMD_MKENT(edit, 2, 0, do_env_edit, "", ""), #endif |
5e2b3e0c5
|
1205 1206 1207 |
#if defined(CONFIG_CMD_ENV_CALLBACK) U_BOOT_CMD_MKENT(callbacks, 1, 0, do_env_callback, "", ""), #endif |
fffad71bc
|
1208 1209 1210 |
#if defined(CONFIG_CMD_ENV_FLAGS) U_BOOT_CMD_MKENT(flags, 1, 0, do_env_flags, "", ""), #endif |
0c79cda01
|
1211 |
#if defined(CONFIG_CMD_EXPORTENV) |
ea882baf9
|
1212 |
U_BOOT_CMD_MKENT(export, 4, 0, do_env_export, "", ""), |
0c79cda01
|
1213 |
#endif |
a000b7950
|
1214 1215 1216 |
#if defined(CONFIG_CMD_GREPENV) U_BOOT_CMD_MKENT(grep, CONFIG_SYS_MAXARGS, 1, do_env_grep, "", ""), #endif |
0c79cda01
|
1217 |
#if defined(CONFIG_CMD_IMPORTENV) |
ea882baf9
|
1218 |
U_BOOT_CMD_MKENT(import, 5, 0, do_env_import, "", ""), |
0c79cda01
|
1219 |
#endif |
ea882baf9
|
1220 1221 1222 1223 1224 1225 1226 1227 |
U_BOOT_CMD_MKENT(print, CONFIG_SYS_MAXARGS, 1, do_env_print, "", ""), #if defined(CONFIG_CMD_RUN) U_BOOT_CMD_MKENT(run, CONFIG_SYS_MAXARGS, 1, do_run, "", ""), #endif #if defined(CONFIG_CMD_SAVEENV) && !defined(CONFIG_ENV_IS_NOWHERE) U_BOOT_CMD_MKENT(save, 1, 0, do_env_save, "", ""), #endif U_BOOT_CMD_MKENT(set, CONFIG_SYS_MAXARGS, 0, do_env_set, "", ""), |
88733e2c6
|
1228 1229 1230 |
#if defined(CONFIG_CMD_ENV_EXISTS) U_BOOT_CMD_MKENT(exists, 2, 0, do_env_exists, "", ""), #endif |
ea882baf9
|
1231 |
}; |
2e5167cca
|
1232 |
#if defined(CONFIG_NEEDS_MANUAL_RELOC) |
60f7da1f4
|
1233 1234 1235 1236 1237 |
void env_reloc(void) { fixup_cmdtable(cmd_env_sub, ARRAY_SIZE(cmd_env_sub)); } #endif |
f3c615b8a
|
1238 |
static int do_env(cmd_tbl_t *cmdtp, int flag, int argc, char * const argv[]) |
ea882baf9
|
1239 1240 |
{ cmd_tbl_t *cp; |
5904da021
|
1241 |
if (argc < 2) |
4c12eeb8b
|
1242 |
return CMD_RET_USAGE; |
5904da021
|
1243 |
|
ea882baf9
|
1244 1245 1246 1247 1248 1249 1250 1251 |
/* drop initial "env" arg */ argc--; argv++; cp = find_cmd_tbl(argv[0], cmd_env_sub, ARRAY_SIZE(cmd_env_sub)); if (cp) return cp->cmd(cmdtp, flag, argc, argv); |
4c12eeb8b
|
1252 |
return CMD_RET_USAGE; |
ea882baf9
|
1253 |
} |
088f1b199
|
1254 1255 |
#ifdef CONFIG_SYS_LONGHELP static char env_help_text[] = |
ea882baf9
|
1256 1257 1258 1259 |
#if defined(CONFIG_CMD_ASKENV) "ask name [message] [size] - ask for environment variable env " #endif |
5e2b3e0c5
|
1260 1261 1262 1263 |
#if defined(CONFIG_CMD_ENV_CALLBACK) "callbacks - print callbacks and their associated variables env " #endif |
b64b7c3df
|
1264 1265 1266 1267 |
"default [-f] -a - [forcibly] reset default environment " "env default [-f] var [...] - [forcibly] reset variable(s) to their default values " |
9d8d661d7
|
1268 1269 |
"env delete [-f] var [...] - [forcibly] delete variable(s) " |
ea882baf9
|
1270 1271 1272 1273 |
#if defined(CONFIG_CMD_EDITENV) "env edit name - edit environment variable " #endif |
88733e2c6
|
1274 1275 1276 1277 |
#if defined(CONFIG_CMD_ENV_EXISTS) "env exists name - tests for existence of variable " #endif |
4796bc4bb
|
1278 |
#if defined(CONFIG_CMD_EXPORTENV) |
37f2fe747
|
1279 1280 |
"env export [-t | -b | -c] [-s size] addr [var ...] - export environment " |
4796bc4bb
|
1281 |
#endif |
fffad71bc
|
1282 1283 1284 1285 |
#if defined(CONFIG_CMD_ENV_FLAGS) "env flags - print variables that have non-default flags " #endif |
a000b7950
|
1286 |
#if defined(CONFIG_CMD_GREPENV) |
be29df6a1
|
1287 1288 1289 1290 |
#ifdef CONFIG_REGEX "env grep [-e] [-n | -v | -b] string [...] - search environment " #else |
d87244d5a
|
1291 1292 |
"env grep [-n | -v | -b] string [...] - search environment " |
a000b7950
|
1293 |
#endif |
be29df6a1
|
1294 |
#endif |
4796bc4bb
|
1295 |
#if defined(CONFIG_CMD_IMPORTENV) |
eaf734724
|
1296 1297 |
"env import [-d] [-t [-r] | -b | -c] addr [size] [var ...] - import environment " |
4796bc4bb
|
1298 |
#endif |
be11235ab
|
1299 1300 |
"env print [-a | name ...] - print environment " |
49d81fdfb
|
1301 1302 1303 1304 |
#if defined(CONFIG_CMD_NVEDIT_EFI) "env print -e [name ...] - print UEFI environment " #endif |
ea882baf9
|
1305 1306 1307 1308 |
#if defined(CONFIG_CMD_RUN) "env run var [...] - run commands in an environment variable " #endif |
d798a9b5d
|
1309 |
#if defined(CONFIG_CMD_SAVEENV) && !defined(CONFIG_ENV_IS_NOWHERE) |
ea882baf9
|
1310 1311 |
"env save - save environment " |
d798a9b5d
|
1312 |
#endif |
49d81fdfb
|
1313 1314 1315 1316 |
#if defined(CONFIG_CMD_NVEDIT_EFI) "env set -e name [arg ...] - set UEFI variable; unset if 'arg' not specified " #endif |
088f1b199
|
1317 1318 1319 1320 1321 1322 1323 |
"env set [-f] name [arg ...] "; #endif U_BOOT_CMD( env, CONFIG_SYS_MAXARGS, 1, do_env, "environment handling commands", env_help_text |
ea882baf9
|
1324 1325 1326 1327 1328 |
); /* * Old command line interface, kept for compatibility */ |
8bde7f776
|
1329 |
|
246c69225
|
1330 |
#if defined(CONFIG_CMD_EDITENV) |
722b061b6
|
1331 |
U_BOOT_CMD_COMPLETE( |
ea882baf9
|
1332 |
editenv, 2, 0, do_env_edit, |
246c69225
|
1333 1334 1335 |
"edit environment variable", "name " |
722b061b6
|
1336 1337 |
" - edit environment variable 'name'", var_complete |
246c69225
|
1338 1339 |
); #endif |
722b061b6
|
1340 |
U_BOOT_CMD_COMPLETE( |
ea882baf9
|
1341 |
printenv, CONFIG_SYS_MAXARGS, 1, do_env_print, |
2fb2604d5
|
1342 |
"print environment variables", |
be11235ab
|
1343 1344 1345 |
"[-a] - print [all] values of all environment variables " |
49d81fdfb
|
1346 1347 1348 1349 1350 1351 |
#if defined(CONFIG_CMD_NVEDIT_EFI) "printenv -e [name ...] " " - print UEFI variable 'name' or all the variables " #endif |
8bde7f776
|
1352 1353 |
"printenv name ... " |
722b061b6
|
1354 1355 |
" - print value of environment variable 'name'", var_complete |
8bde7f776
|
1356 |
); |
a000b7950
|
1357 1358 1359 1360 |
#ifdef CONFIG_CMD_GREPENV U_BOOT_CMD_COMPLETE( grepenv, CONFIG_SYS_MAXARGS, 0, do_env_grep, "search environment variables", |
be29df6a1
|
1361 1362 1363 1364 |
#ifdef CONFIG_REGEX "[-e] [-n | -v | -b] string ... " #else |
d87244d5a
|
1365 1366 |
"[-n | -v | -b] string ... " |
be29df6a1
|
1367 |
#endif |
d87244d5a
|
1368 1369 |
" - list environment name=value pairs matching 'string' " |
be29df6a1
|
1370 1371 1372 1373 |
#ifdef CONFIG_REGEX " \"-e\": enable regular expressions; " #endif |
d87244d5a
|
1374 1375 1376 |
" \"-n\": search variable names; \"-v\": search values; " " \"-b\": search both names and values (default)", |
a000b7950
|
1377 1378 1379 |
var_complete ); #endif |
722b061b6
|
1380 |
U_BOOT_CMD_COMPLETE( |
ea882baf9
|
1381 |
setenv, CONFIG_SYS_MAXARGS, 0, do_env_set, |
2fb2604d5
|
1382 |
"set environment variables", |
49d81fdfb
|
1383 1384 1385 1386 1387 1388 1389 1390 1391 1392 |
#if defined(CONFIG_CMD_NVEDIT_EFI) "-e name [value ...] " " - set UEFI variable 'name' to 'value' ...' " " - delete UEFI variable 'name' if 'value' not specified " #endif "setenv [-f] name value ... " |
24ab5a191
|
1393 1394 1395 1396 1397 |
" - [forcibly] set environment variable 'name' to 'value ...' " "setenv [-f] name " " - [forcibly] delete environment variable 'name'", |
722b061b6
|
1398 |
var_complete |
8bde7f776
|
1399 |
); |
c76fe4742
|
1400 |
#if defined(CONFIG_CMD_ASKENV) |
8bde7f776
|
1401 |
|
0d4983930
|
1402 |
U_BOOT_CMD( |
ea882baf9
|
1403 |
askenv, CONFIG_SYS_MAXARGS, 1, do_env_ask, |
2fb2604d5
|
1404 |
"get environment variables from stdin", |
8bde7f776
|
1405 1406 |
"name [message] [size] " |
7d85591dd
|
1407 |
" - get environment variable 'name' from stdin (max 'size' chars)" |
8bde7f776
|
1408 |
); |
902531788
|
1409 |
#endif |
8bde7f776
|
1410 |
|
c76fe4742
|
1411 |
#if defined(CONFIG_CMD_RUN) |
722b061b6
|
1412 |
U_BOOT_CMD_COMPLETE( |
6d0f6bcf3
|
1413 |
run, CONFIG_SYS_MAXARGS, 1, do_run, |
2fb2604d5
|
1414 |
"run commands in an environment variable", |
8bde7f776
|
1415 1416 |
"var [...] " |
722b061b6
|
1417 1418 |
" - run the commands in the environment variable(s) 'var'", var_complete |
8bde7f776
|
1419 |
); |
902531788
|
1420 |
#endif |
7ac2fe2da
|
1421 |
#endif /* CONFIG_SPL_BUILD */ |