summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMike Frysinger <vapier@gentoo.org>2009-05-24 02:26:19 -0400
committerWolfgang Denk <wd@denx.de>2009-06-12 20:45:48 +0200
commit4c94f6c54bbc4dc5f418da01d8ec01e2adf636be (patch)
treefd2cda9d5f298aa359a1bf69dd19adfce1a4bc55
parent3112030a430553768de5d30c05bedf8710784452 (diff)
nvedit: speed up printing of environment
The printing code would check the same environment byte multiple times and write to the console one byte at a time. For some devices (such as the Blackfin JTAG console which operates in 8 bytes at a time), this is pretty damned slow. So create a small 16 byte buffer to fill up and send to puts as needed. In the process, unify the different print functions, shrink the resulting code (source and compiled), and avoid excess env reads as those too can be somewhat expensive depending on the board. Signed-off-by: Mike Frysinger <vapier@gentoo.org>
-rw-r--r--common/cmd_nvedit.c94
1 files changed, 55 insertions, 39 deletions
diff --git a/common/cmd_nvedit.c b/common/cmd_nvedit.c
index 3ee971ab0e..ac9e5cfc32 100644
--- a/common/cmd_nvedit.c
+++ b/common/cmd_nvedit.c
@@ -94,56 +94,72 @@ int get_env_id (void)
* Command interface: print one or all environment variables
*/
-int do_printenv (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+/*
+ * state 0: finish printing this string and return (matched!)
+ * state 1: no matching to be done; print everything
+ * state 2: continue searching for matched name
+ */
+static int printenv(char *name, int state)
{
- int i, j, k, nxt;
- int rcode = 0;
-
- if (argc == 1) { /* Print all env variables */
- for (i=0; env_get_char(i) != '\0'; i=nxt+1) {
- for (nxt=i; env_get_char(nxt) != '\0'; ++nxt)
- ;
- for (k=i; k<nxt; ++k)
- putc(env_get_char(k));
- putc ('\n');
-
- if (ctrlc()) {
- puts ("\n ** Abort\n");
- return 1;
+ int i, j;
+ char c, buf[17];
+
+ i = 0;
+ buf[16] = '\0';
+
+ while (state && env_get_char(i) != '\0') {
+ if (state == 2 && envmatch((uchar *)name, i) >= 0)
+ state = 0;
+
+ j = 0;
+ do {
+ buf[j++] = c = env_get_char(i++);
+ if (j == sizeof(buf) - 1) {
+ if (state <= 1)
+ puts(buf);
+ j = 0;
}
- }
+ } while (c != '\0');
- printf("\nEnvironment size: %d/%ld bytes\n",
- i, (ulong)ENV_SIZE);
+ if (state <= 1) {
+ if (j)
+ puts(buf);
+ putc('\n');
+ }
- return 0;
+ if (ctrlc())
+ return -1;
}
- for (i=1; i<argc; ++i) { /* print single env variables */
- char *name = argv[i];
+ if (state == 0)
+ i = 0;
+ return i;
+}
- k = -1;
+int do_printenv (cmd_tbl_t *cmdtp, int flag, int argc, char *argv[])
+{
+ int i;
+ int rcode = 0;
- for (j=0; env_get_char(j) != '\0'; j=nxt+1) {
+ if (argc == 1) {
+ /* print all env vars */
+ rcode = printenv(NULL, 1);
+ if (rcode < 0)
+ return 1;
+ printf("\nEnvironment size: %d/%ld bytes\n",
+ rcode, (ulong)ENV_SIZE);
+ return 0;
+ }
- for (nxt=j; env_get_char(nxt) != '\0'; ++nxt)
- ;
- k = envmatch((uchar *)name, j);
- if (k < 0) {
- continue;
- }
- puts (name);
- putc ('=');
- while (k < nxt)
- putc(env_get_char(k++));
- putc ('\n');
- break;
- }
- if (k < 0) {
- printf ("## Error: \"%s\" not defined\n", name);
- rcode ++;
+ /* print selected env vars */
+ for (i = 1; i < argc; ++i) {
+ char *name = argv[i];
+ if (printenv(name, 2)) {
+ printf("## Error: \"%s\" not defined\n", name);
+ ++rcode;
}
}
+
return rcode;
}